Continue to Site

Welcome to our site!

Electro Tech is an online community (with over 170,000 members) who enjoy talking about and building electronic circuits, projects and gadgets. To participate you need to register. Registration is free. Click here to register now.

  • Welcome to our site! Electro Tech is an online community (with over 170,000 members) who enjoy talking about and building electronic circuits, projects and gadgets. To participate you need to register. Registration is free. Click here to register now.

C programming structures: why do both these examples work?

Status
Not open for further replies.

blueroomelectronics

Well-Known Member
I'm just learning C (Microchips XC8) and its been great fun to learn.

Some examples show
Code:
struct Goo{
    int Day;
    int Month;
    int Year;
};
struct Goo Date;
But this works too. Are they the same thing?
Code:
struct {
    int Day;
    int Month;
    int Year;
} Date;
But I don't see a way to initialize that one. So
Code:
struct Goo { // declare placeholder
    int Day;
    int Month;
    int Year;
};
struct Goo Date = {2, 4, 5}; // create & initialize variable Date
 
Last edited:
In the first example you've created a named struct, which you then use as a type to define the variable Date.

In the second example you create an unnamed/anonymous struct, which you use to define the variable Date. Both variables have the same organisation and member variable names, but you can't use the latter as a function parameter or return type (but you can use it as a local or global variable, or within another struct or union if the compiler supports it).

Another example, where we are creating a named struct typedef
Code:
typedef struct{
    int Day;
    int Month;
    int Year;
}Goo;
Goo Date;

// example function prototype:
Goo AddToDate(Goo startDate, int secondsToAdd);

// whereas without the typedef you'd have to use
struct Goo AddToDate(struct Goo startDate, int secondsToAdd);
 
Thanks dougy83. My ancient brain is on overload. I'm more a digital hardware guy.

Now I'll have to look up typedef.
How would you initialize the named structure? e.g. = {x,y,z};
Another confusing symbol is "->"
 
Typedef is just to allow you to write things in shorthand, or to alias types, etc.

An example program showing how the structures can be initialised. Note that the form ".x = 3" requires the compiler to understand the notation (C99 does).
Code:
#include <stdio.h>

struct TestStruct
{
    int x, y, z;
};

void printMyStruct(struct TestStruct *structPointer);

int main()
{
    {
        struct TestStruct ts = {1, 2, 3};
        printf("A..   %d, %d, %d\n", ts.x, ts.y, ts.z);
        printMyStruct(&ts); // pass in the address of ts
    }
    {
        struct TestStruct ts = {.y = 1, .x = 2, .z = 3};
        printf("B..   %d, %d, %d\n", ts.x, ts.y, ts.z);
        printMyStruct(&ts); // pass in the address of ts
    }
}

void printMyStruct(struct TestStruct *structPointer)
{
    printf("ptr.. %d, %d, %d\n", structPointer->x, (*structPointer).y, structPointer->z);  // showing two different ways to access the member variables
}

The output will be
Code:
A..   1, 2, 3
ptr.. 1, 2, 3
B..   2, 1, 3
ptr.. 2, 1, 3

The -> symbol is for accessing struct members when you only have a pointer to the structure and the example is shown in the printMyStruct() function. You will see that structPointer->x and (*structPointer).x are equivalent.
 
C

"-> " is a pointer.
The best is to go back and buy or find the original C book by Kernigan and Richie. There are may others.
Consider C is a "low" level language parading around as a "high" level language.

Aug
 
Again thanks, I do have the K&R ANSI C book. Reading is one thing, digesting is another.

I see you assign and initialize the structure in main(), is there any reason not to do this outside of main()? I noticed any variables declared outside of any function become volatile global. Is that bad form?
 
I see you assign and initialize the structure in main(), is there any reason not to do this outside of main()?
If declared outside of main they will be global. You will see that I've declared them not only within main(), but also within their own block. This means the variable is not accessible outside of the block it is declared in. I only used the structure inside of main, so that's where I declared them.

This can be useful for e.g. temporary variables used in functions; you don't really want to keep the variables after calling the function, so if you declare them in the function they can be discarded when the function exits (or you leave the block) (well the memory they use can be reused for some other variables in some other function/block).

I noticed any variables declared outside of any function become volatile global. Is that bad form?
They will be global; they won't become volatile. Yes, it's bad form if they don't need to be global.
 
Status
Not open for further replies.

Latest threads

New Articles From Microcontroller Tips

Back
Top