C ProgrammingUnit 88 min read
Unit 8: Structures, Nested Structures & Unions – Key Concepts
Unit 8 of C Programming: introduces structures and unions, their syntax, memory layout, initialization, nested structures, pointers, typedefs, and practical applications such as student records and book catalogs.
Key points
- A structure groups heterogeneous data into a single composite type.
- Nested structures allow hierarchical data modeling and are accessed with the dot operator.
- A union shares memory among its members, saving space when only one member is used at a time.
- `typedef` simplifies complex type names and improves code readability.
- Understanding memory layout of structs and unions is essential for efficient data handling and debugging.
1. Introduction to Structures
A structure (struct) is a user‑defined composite data type that groups variables of different types under a single name.
struct Student {
int sid;
char name[50];
char address[100];
float cgpa;
};
- Member variables can be of any type: primitive, arrays, pointers, or even other structures.
- The structure itself is a type; variables of that type are called structure objects.
1.1 Syntax & Declaration
struct tag_name { /* member declarations */ }; // tag_name is optional
- Tag: optional identifier used to refer to the structure type later.
- Anonymous struct: no tag; must be used immediately or with
typedef.
1.2 Memory Layout
+-----------------+-----------------+-----------------+-----------------+
| sid | name[50] | address[100] | cgpa |
+-----------------+-----------------+-----------------+-----------------+
- Each member occupies its natural alignment; the compiler may insert padding for alignment.
- Size of struct = sum of member sizes + padding.
1.3 Initialization
struct Student s1 = { 101, "Ram", "KTM", 3.75 };
- Designated initializers (C99) allow specifying members by name:
struct Student s2 = { .sid = 102, .name = "Sita", .cgpa = 3.90 }; - Uninitialized members receive zero (for static storage) or indeterminate values (for automatic storage).
1.4 Accessing Members
- Dot operator (
.) for objects:s1.cgpa. - Arrow operator (
->) for pointers:struct Student *p = &s1; printf("%f", p->cgpa);
2. Nested Structures
A structure can contain another structure as a member, enabling hierarchical data representation.
struct Address {
char city[30];
char country[30];
};
struct Student {
int sid;
char name[50];
struct Address addr;
float cgpa;
};
2.1 Accessing Nested Members
printf("%s, %s", s1.addr.city, s1.addr.country);
2.2 Example: Fibonacci Prime Check
Problem: Determine whether the nth Fibonacci number is prime.
Solution: Use nested structures to store Fibonacci term and its primality flag.
#include <stdio.h>
#include <stdbool.h>
struct FibInfo {
unsigned long long term;
bool isPrime;
};
bool isPrime(unsigned long long n) {
if (n < 2) return false;
for (unsigned long long i = 2; i * i <= n; ++i)
if (n % i == 0) return false;
return true;
}
int main(void) {
int n;
printf("Enter n: ");
scanf("%d", &n);
struct FibInfo fib = {0, false};
unsigned long long a = 0, b = 1;
for (int i = 1; i <= n; ++i) {
fib.term = b;
a = b;
b = a + b;
}
fib.isPrime = isPrime(fib.term);
printf("Fib(%d) = %llu is %sprime.\n",
n, fib.term, fib.isPrime ? "" : "not ");
return 0;
}
Trace for n = 7
| i | a | b | fib.term | isPrime |
|---|---|---|---|---|
| 1 | 0 | 1 | 1 | false |
| 2 | 1 | 1 | 1 | false |
| 3 | 1 | 2 | 2 | true |
| 4 | 2 | 3 | 3 | true |
| 5 | 3 | 5 | 5 | true |
| 6 | 5 | 8 | 8 | false |
| 7 | 8 | 13 | 13 | true |
Result: Fib(7) = 13 is prime.
3. Unions
A union is a special data type where all members share the same memory location. Only one member can hold a value at a time.
union Data {
int i;
float f;
char str[20];
};
3.1 Memory Layout
+-----------------+
| i / f / str[20]|
+-----------------+
- Size of union = size of its largest member (plus padding).
3.2 Advantages
- Memory efficiency: useful when a variable can hold one of several types.
- Variant data representation: e.g., a packet header that can be interpreted differently.
3.3 Disadvantages
- No type safety: programmer must remember which member is active.
- Limited to one active member: storing multiple values simultaneously is impossible.
3.4 Example: Variant Data
#include <stdio.h>
union Value {
int i;
float f;
char c;
};
int main(void) {
union Value v;
v.i = 42;
printf("int: %d\n", v.i);
v.f = 3.14f; // overwrites previous int
printf("float: %f\n", v.f);
v.c = 'A';
printf("char: %c\n", v.c);
return 0;
}
4. Struct vs Array vs Union
| Feature | Structure | Array | Union |
|---|---|---|---|
| Members | Heterogeneous | Homogeneous | Heterogeneous |
| Memory | Sum of members + padding | N * size of element | Size of largest member |
| Access | . or -> |
[] |
. or -> |
| Use case | Record of related data | Sequence of same type | Variant data sharing memory |
| Size | Fixed (depends on members) | Fixed (depends on N) | Fixed (size of largest member) |
4.1 Struct vs Array
- Struct groups different data types; Array stores same type.
- Example:
struct Point { int x; int y; };vsint arr[2];
4.2 Struct vs Union
- Struct allocates separate memory for each member.
- Union shares memory; only one member is valid at a time.
5. Typedef and Aliases
typedef creates an alias for a type, simplifying complex declarations.
typedef struct {
int sid;
char name[50];
char address[100];
float cgpa;
} Student;
Now we can declare:
Student s1, s2;
5.1 Typedef for Unions
typedef union {
int i;
float f;
char str[20];
} Data;
6. Pointers to Structures
Pointers to structures are essential for dynamic memory allocation and linked data structures.
Student *p = malloc(sizeof(Student));
p->sid = 103;
6.1 Array of Pointers to Structs
Student *students[10];
for (int i = 0; i < 10; ++i)
students[i] = malloc(sizeof(Student));
7. Practical Applications
| Application | Structure/Union Used | Why |
|---|---|---|
| Student database | struct Student |
Stores heterogeneous student data. |
| Book catalog | struct Book |
Each book has title, author, price. |
| Graphics vertex | struct Vertex { float x, y, z; } |
Group coordinates. |
| Network packet | union Packet { Header h; Data d; } |
Variant packet types. |
| Embedded systems | union { uint8_t b; struct { uint4_t a:4; uint4_t b:4; } bits; } |
Bit‑field manipulation. |
7.1 Example: Book Catalog
typedef struct {
char title[100];
char author[50];
float price;
} Book;
int main(void) {
Book books[50];
for (int i = 0; i < 50; ++i) {
printf("Enter details for book %d:\n", i+1);
scanf("%99s %49s %f", books[i].title, books[i].author, &books[i].price);
}
// Display books priced above 500
printf("\nBooks priced above 500:\n");
for (int i = 0; i < 50; ++i)
if (books[i].price > 500)
printf("%s by %s, Price: %.2f\n", books[i].title, books[i].author, books[i].price);
return 0;
}
8. Common Mistakes & Debugging Tips
| Mistake | Explanation | Fix |
|---|---|---|
Using . instead of -> on a pointer |
Compile error or wrong access | Use -> for pointers |
| Forgetting to allocate memory for struct pointer | Segmentation fault | malloc or calloc before use |
| Overlooking padding in struct | Miscalculating size | Use sizeof and offsetof |
| Accessing inactive union member | Undefined behavior | Keep track of active member or use a tag field |
9. Summary
- Structures group related data; memory layout is contiguous.
- Nested structures enable hierarchical modeling.
- Unions share memory; useful for variant data.
- Typedef improves readability.
- Pointers to structs are essential for dynamic data structures.
- Understanding memory layout aids in efficient coding and debugging.
Exam tip
Code Writing
- Expect to write complete programs: define structs/unions, initialize, input/output, and conditional logic.
- Practice initializing with designated initializers and using
typedef.
Conceptual Questions
- Be ready to explain memory layout, padding, and differences between struct and union.
- Compare struct vs array vs union in a table.
Trace & Debug
- Given a small program, trace the values of struct members or union fields.
- Identify which member is active in a union after assignments.
Practical Scenarios
- Design a struct for a real‑world entity (e.g., student, book, employee).
- Use nested structs to model addresses or dates.
Time Management
- Allocate 30 % of the exam time to coding, 30 % to conceptual questions, 40 % to tracing/debugging.
Focus on clarity, correct syntax, and logical flow. Good luck!
Based on the TU BSc CSIT syllabus for C Programming (CSC115), unit 8.
Discussion
Loading…