Created: 2023-08-20 18:00
Status: #concept
Subject: Programming
Tags: C Object Data Structure TypeScript interface JavaScript Class
struct
A
struct
is a data structure in C that contains named members that may have different types.
- the members inside the struct have their own Local Scope, so two different struct tags can have the same member names.
Syntax
It is similar to
type variableName
with int
, float
, or double
, but we use a struct Tag { ...members }
instead.
- the sizeof a structure depends on the members, allocated 1 by 1 and with enough space for all.
- however, this size is not always accurate as the compiler may allocate more space to create a Computer Word (typically 8 Bytes).
- the
Tag
is optional.
struct Tag { ...members } variableName;
// Part represents a part in a warehouse with an ID 'number', 'id', and stock 'on_hand'
// we declare 2 variables 'part1' & 'part2' with the type Part
struct Part {
int id;
char name[NAME_LEN+1];
int on_hand;
} part1, part2;
struct Part part3 = { 10, "Engine", 43 }; // using struct Tag to initialize
Initialization
struct Tag { ...members } variable = { ...memberValues };
struct {
int id;
char name[NAME_LEN+1];
int on_hand;
} part1 = {528, "Disk drive", 10},
part2 = {914, "Printer cable", 5},
part3 = {.on_hand = 2}; // we can also initialize specified members
// each value, separated by commas, will be stored in each member - in order
Member Access
We use the Dot Operator
.
, similar to other Object-oriented programming languages.
- the
.
operator has the same precedence as()
or->
. - they are treated as Lvalues and can be assigned as Variables.
printf("Part id: %d", part1.id);
printf("Part name: %s", part1.name);
printf("Quantity on hand: %d", part1.on_hand);
part1.number = 258;
part1.on_hand++;
Copying Members & Assignment
Since we allocate a static amount of memory, we can assign them as if they were normal Variable C Data Types like
int
.
- this only works for compatible types like structs with the same
Tag
, it will not work if thestruct
was declared separately.
struct {
int a[10];
} a1, a2;
struct {
int a[10];
} b;
a1 = a2; // valid
b = a1; // invalid, not compatible
By extension of that, we can also directly assign structs into Function parameters.
void print_part(struct part p) // function definition
{
printf("Part id: %d\n", p.id);
printf("Part name: %s\n", p.name);
printf("Quantity on hand: %d\n" p.on_hand);
}
print_part(part1); // function call
Custom Types with struct
& typedef
Instead of using
struct Tag
to declare a struct variable, we can alias the struct Tag
with typedef
.
typedef type Alias
typedef struct node {
int data;
struct node *next;
} Node;
Node head = { 3, NULL };
Nested struct
Types
- we access them normally with another
.
operator. parent.member.nestedMember
Array of struct
Types
struct dialog_code {
char *country; // use a pointer to a string variable to not mutate
int code;
};
const struct dialing_code country_codes[] =
{
{"Argentina", 54}, {"Bangladesh", 880}, {"Brazil", 55}, {"China", 86},
{"Colombia", 57}, {"Egypt", 20}, {"Ethiopia", 251}, {"Indonesia", 62}
};
struct part inventory[100];
// declaration of array containing a max of 100 'part' structs
print_part(inventory[i]);
// prints the members' values using the function print_part
// on part 'i' in the array 'inventory'
inventory[i].number = 883;
// accessing a member inside part 'i' inside the structs array 'inventory'
inventory[i].name[0] = '\0';
// accessing a char array member inside part 'i'
We can think of
struct
arrays as tables, where the struct.members
are the columns while each struct tag arr[]
element is a row.