C++ Proper use of struct in function arguments [duplicate] - c++

This question already has answers here:
using struct keyword in variable declaration in C++
(6 answers)
Closed 6 years ago.
Quick Question about passing a struct as a function arg. Maybe its a carry over from C that makes no difference in C++.
In many Linked List examples you see them re-declare the word struct in any function argument that takes a struct and I don't understand why. Or any allocation for that matter. A structure is its own object and declaring just the name of the struct is sufficient.
Example:
struct Node{
int data;
Node * next;
};
// Function to output data.
void printNode(struct Node* myNode){
// Print data of node
}
why is the word struct re-declared in the function arg. Declaring type Node* works just fine.
Thanks.

There is a difference between C and C++ use of declarations produced with struct keyword:
In C, struct defines a new struct tag, but not a new type
In C++, struct defines a new type.
The consequence is that C++ lets you use the name defined in struct, while C requires you to either prefix a struct to the tag, or use typedef to define a new type.

C requires it. C++ does not require it, but allows it for backward compatibility. Do not do this for new code.

Related

Get type of instantiated unnamed struct [duplicate]

This question already has answers here:
Can an unnamed struct be made static?
(2 answers)
Passing anonymous structures to functions as parameter using C++ [duplicate]
(3 answers)
Closed 9 months ago.
I'm writing an app in C++ that interfaces with some code written in C.
The following is a simplified version of a struct defined in C code that I can't modify.
struct event{
uint8_t type;
union {
struct /* WishThisHadAName */ {
// ...
} connect;
struct {
// ...
} disconnect;
};
};
I'm trying to be able to define functions that take a pointer to the different unnamed structs, connect, disconnect, and all the others not listed above. To look something like the following.
void onConnect( struct WishThisHadAName *evt );
Is it possible to create this prototype without modifying the original C struct? Is there an easy way to create a wrapper for the unnamed structs to give them a name? Am I forced to create named structs that mirror the unnamed ones I'm trying to use?
I know you can get the type of an instantiated variable with decltype but I can't figure out how I could use that or declval in order to create the function prototype I'm looking for.
Simple as using event_connect_t = decltype(event::connect);.
Then you can use it as void onConnect( event_connect_t *evt );.
You can't declare a compatible type, but you can just extract the existing type declaration from the definition. decltype can resolve static member references just fine.
If you're using a compiler such as gcc/g++, you can use typeof to create a typedef for the anonymous type:
typedef __typeof__(((struct event){0}).connect) conn_type;
typedef __typeof__(((struct event){0}).disconnect) disconn_type;
Or without compound literals:
struct event e;
typedef __typeof__(e.connect) t1;
typedef __typeof__(e.disconnect) t2;

C++ iterate through struct by increasin pointer bit by bit [duplicate]

This question already has answers here:
Iterate through Struct and Class Members [duplicate]
(6 answers)
Closed 5 years ago.
I am currently trying to iterate through a struct var in C++. I've got a struct var but I need to access specific elements of the struct.
someStruct {
int a;
int b;
bool c;
...
};
&someStructVar+1 would increase the memory by the size of the struct. But I need to increase the memory address by one bit after another. Is this possible? Is there any other approach?
What you're asking for is reflection, which C does not support. You can't get a list of fields of a struct and iterate through them.
You'll need to explicitly call out each field by name.
You can't "iterate" members of struct through pointer arithemetics, this is not allowed in C++.
The only thing you can iterate with pointer arithemtics are C-style arrays.

define struct and use as parameter [duplicate]

This question already has answers here:
Arduino: struct pointer as function parameter
(4 answers)
Closed 7 years ago.
I'm working on my Arduino project, which is the only C/C++ compiler I'm using.
I'm stumbling on why I cannot use the struct as a type on my function parameter.
Not sure if this specific to Arduino compiler design, or general C/C++ programming.
struct myStruct_t {
byte var1;
byte var2;
};
myStruct_t myStruct;
void setup() {
}
void loop() {
}
void myFunc(myStruct_t *myVar) {
int i = 0;
}
This results in a compiler errors:
error: variable or field 'myFunc' declared void
error: 'myStruct_t' was not declared in this scope
error: 'myVar' was not declared in this scope
If I comment out the declaration of the "myFunc" then it compiles as is.
I'm not clear on why I can declare and use a variable of that structure, however I can use the structure as a parameter type. Does the "struct" type not act as a type for parameter use?
Thanks.
Because in c you need to typedef to achieve that, otherwise you need to use struct to refer to the structure.
I'd recommend against typedefing and also against the _t in the structure name, but if you want it that way just do this
typedef struct myStruct_t {
byte var1;
byte var2;
} myStruct_t;
and do not use global variables, pass variables as parameters.

Why are structures typedef'ed to their own names? [duplicate]

This question already has answers here:
Difference between 'struct' and 'typedef struct' in C++?
(8 answers)
Closed 8 years ago.
In many places in code I have seen code like this:
typedef struct Name_of_Struct{
//Things that the struct holds
} Name_of_Struct;
I don't seem to understand why such a declaration? Why is a struct typedef'ed to its own name? Isn't it like saying typedef Name_of_struct Name_of_Struct; ? I know there must be some reason behind such a declaration, as such instances of code are seen in good and highly used code bases like SDL.
In C++ you don't have to do that
However in C this is done in order to save some typing
struct Name_of_Struct{
//Things that the struct holds
} ;
struct Name_of_Struct ss; // If not typedef'ed you'll have to use `struct`
But with typedef
typedef struct Name_of_Struct{
//Things that the struct holds
} Name_of_Struct;
Name_of_Struct ss ; // Simply just use name of struct, avoid struct everywhere
The code is probably shared between C and C++. The C Programming Language does not automatically create type names for user-created types (e.g., enum, struct, union). I haven't written a lot of C in recent years so this may have been changed in C99.
Specifying the name twice is redundant.
Originally in C the typedef was used so you didn't need to qualify the name with struct all the time. In C++ you can simply name the struct.
// C method
struct MyStruct {};
// need to qualify that name with `struct`
struct MyStruct s;
// C method avoiding typing `struct` all the time
typedef struct {} MyStruct;
MyStruct s; // no need to use `struct`
// C++ way
struct MyStruct {};
MyStruct s;
It seems some programmers have made a Frankenstein of the two methods.

Forward declaring a typedef of an unnamed struct [duplicate]

This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
Forward declarations of unnamed struct
If I have
typedef struct tagPAGERANGE
{
int iFirstPage;
int iLastPage;
} PAGERANGE;
I can forward declare it that way
struct tagPAGERANGE;
typedef struct tagPAGERANGE PAGERANGE;
But what I have is
typedef struct
{
int iFirstPage;
int iLastPage;
} PAGERANGE;
I'm not sure how I can do it. I only want to hold a pointer to this struct. Right now I'm stuck with either including a rather substantial header, or duplicating the definition of the struct.
It's impossible. You can only declare named structs.
Think about what identifies a struct that doesn't have a name, and how do you tell the compiler that it's that struct you want. If it doesn't have a name, it's identified by its members, so you need to provide members — i.e. define it. Therefore, you can't just declare it — you don't have a luxury of an identifier other than the definition itself.
Since this is used in a C++ code, just get rid of the typedefs altogether, they are unnecessary and bad style in C++.
The real solution is to just use named structs:
struct foo; // forward declaration
struct foo {
// … implementation
};
The typedefs are not useful.