Complete guide to arrays of structures in C — declaring and initializing struct arrays, student database example, sorting, searching, passing to functions, practical examples with output.
When you need to handle multiple records of the same type — students, employees, products, books — you combine two powerful concepts: arrays and structures. An array of structures gives you a table-like collection where each element is a complete record.
Declaration and Initialization
#include <stdio.h>
struct Student {
int roll;
char name[50];
float marks;
};
int main() {
// Method 1: Initialize at declaration
struct Student class_a[3] = {
{1, "Alice", 92.5},
{2, "Bob", 88.0},
{3, "Charlie", 95.3}
};
// Method 2: Assign individually
struct Student class_b[3];
class_b[0].roll = 4;
// ... and so on
// Access
for (int i = 0; i < 3; i++) {
printf("Roll: %d | Name: %-10s | Marks: %.1f\n",
class_a[i].roll, class_a[i].name, class_a[i].marks);
}
return 0;
}
Roll: 1 | Name: Alice | Marks: 92.5
Roll: 2 | Name: Bob | Marks: 88.0
Roll: 3 | Name: Charlie | Marks: 95.3
Memory Layout
struct Student class_a[3];
┌───────────────────────┬───────────────────────┬───────────────────────┐
│ class_a[0] │ class_a[1] │ class_a[2] │
│ roll│name[50]│marks │ roll│name[50]│marks │ roll│name[50]│marks │
│ 1 │"Alice" │92.5 │ 2 │"Bob" │88.0 │ 3 │"Charlie"│95.3 │
└───────────────────────┴───────────────────────┴───────────────────────┘
Address: base base + sizeof(Student) base + 2*sizeof(Student)
Each element is stored contiguously, making array access efficient.
Student Database — Complete Example
#include <stdio.h>
#include <string.h>
#define MAX_STUDENTS 100
struct Student {
int roll;
char name[50];
float marks[5]; // 5 subjects
float average;
};
void calculate_average(struct Student *s) {
float total = 0;
for (int i = 0; i < 5; i++) {
total += s->marks[i];
}
s->average = total / 5.0;
}
char *get_grade(float avg) {
if (avg >= 90) return "A+";
if (avg >= 80) return "A";
if (avg >= 70) return "B";
if (avg >= 60) return "C";
return "F";
}
int main() {
struct Student students[] = {
{101, "Alice", {95, 88, 92, 97, 90}, 0},
{102, "Bob", {78, 82, 75, 80, 85}, 0},
{103, "Charlie", {90, 91, 88, 95, 93}, 0},
{104, "Diana", {65, 70, 62, 68, 72}, 0},
{105, "Eve", {55, 60, 58, 62, 50}, 0}
};
int n = 5;
// Calculate averages
for (int i = 0; i < n; i++) {
calculate_average(&students[i]);
}
// Print report card
printf("╔══════╦════════════╦═════════╦═══════╗\n");
printf("║ Roll ║ Name ║ Average ║ Grade ║\n");
printf("╠══════╬════════════╬═════════╬═══════╣\n");
for (int i = 0; i < n; i++) {
printf("║ %4d ║ %-10s ║ %5.1f ║ %-2s ║\n",
students[i].roll, students[i].name,
students[i].average, get_grade(students[i].average));
}
printf("╚══════╩════════════╩═════════╩═══════╝\n");
return 0;
}
╔══════╦════════════╦═════════╦═══════╗
║ Roll ║ Name ║ Average ║ Grade ║
╠══════╬════════════╬═════════╬═══════╣
║ 101 ║ Alice ║ 92.4 ║ A+ ║
║ 102 ║ Bob ║ 80.0 ║ A ║
║ 103 ║ Charlie ║ 91.4 ║ A+ ║
║ 104 ║ Diana ║ 67.4 ║ C ║
║ 105 ║ Eve ║ 57.0 ║ F ║
╚══════╩════════════╩═════════╩═══════╝
Sorting an Array of Structures
#include <stdio.h>
#include <string.h>
struct Employee {
int id;
char name[50];
float salary;
};
// Sort by salary (descending) using bubble sort
void sort_by_salary(struct Employee arr[], int n) {
for (int i = 0; i < n - 1; i++) {
for (int j = 0; j < n - i - 1; j++) {
if (arr[j].salary < arr[j + 1].salary) {
struct Employee temp = arr[j];
arr[j] = arr[j + 1];
arr[j + 1] = temp;
}
}
}
}
int main() {
struct Employee team[] = {
{1, "Alice", 75000},
{2, "Bob", 92000},
{3, "Charlie", 68000},
{4, "Diana", 85000}
};
int n = 4;
sort_by_salary(team, n);
printf("Employees sorted by salary (highest first):\n");
for (int i = 0; i < n; i++) {
printf(" %s: $%.0f\n", team[i].name, team[i].salary);
}
return 0;
}
Employees sorted by salary (highest first):
Bob: $92000
Diana: $85000
Alice: $75000
Charlie: $68000
Searching in a Struct Array
#include <stdio.h>
#include <string.h>
struct Product {
int id;
char name[50];
float price;
};
int search_by_name(struct Product arr[], int n, const char *target) {
for (int i = 0; i < n; i++) {
if (strcmp(arr[i].name, target) == 0) {
return i;
}
}
return -1; // Not found
}
int main() {
struct Product catalog[] = {
{1, "Laptop", 999.99},
{2, "Mouse", 29.99},
{3, "Keyboard", 79.99},
{4, "Monitor", 349.99}
};
int n = 4;
const char *search = "Keyboard";
int idx = search_by_name(catalog, n, search);
if (idx >= 0) {
printf("Found '%s' at index %d (Price: $%.2f)\n",
catalog[idx].name, idx, catalog[idx].price);
} else {
printf("'%s' not found.\n", search);
}
return 0;
}
Found 'Keyboard' at index 2 (Price: $79.99)
Passing Struct Arrays to Functions
#include <stdio.h>
struct Point {
float x, y;
};
// Array decays to pointer
float total_distance(struct Point pts[], int n) {
float dist = 0;
for (int i = 1; i < n; i++) {
float dx = pts[i].x - pts[i-1].x;
float dy = pts[i].y - pts[i-1].y;
dist += sqrt(dx*dx + dy*dy);
}
return dist;
}
Dynamic Array of Structures
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
struct Contact {
char name[50];
char phone[15];
};
int main() {
int n;
printf("How many contacts? ");
scanf("%d", &n);
struct Contact *phonebook = (struct Contact *)malloc(n * sizeof(struct Contact));
if (phonebook == NULL) return 1;
for (int i = 0; i < n; i++) {
printf("Contact %d name: ", i + 1);
scanf(" %[^\n]", phonebook[i].name);
printf("Contact %d phone: ", i + 1);
scanf(" %[^\n]", phonebook[i].phone);
}
printf("\n--- Phonebook ---\n");
for (int i = 0; i < n; i++) {
printf(" %s: %s\n", phonebook[i].name, phonebook[i].phone);
}
free(phonebook);
return 0;
}
How many contacts? 2
Contact 1 name: John
Contact 1 phone: 555-1234
Contact 2 name: Jane
Contact 2 phone: 555-5678
--- Phonebook ---
John: 555-1234
Jane: 555-5678
Interview Questions
Q1: How do you sort an array of structures using qsort()?
Use qsort() with a custom comparison function:
int compare_by_name(const void *a, const void *b) {
return strcmp(((struct Student *)a)->name, ((struct Student *)b)->name);
}
qsort(students, n, sizeof(struct Student), compare_by_name);
Q2: What is the difference between an array of structures and a structure containing arrays?
Array of structures: multiple records, each with several fields (a table). Structure containing arrays: one record with array-type fields (like one student with multiple marks). They're different data models.
Q3: Can you return an array of structures from a function?
Not directly (arrays can't be returned in C). You can: (1) pass the array as a parameter, (2) allocate dynamically with malloc and return the pointer, or (3) wrap the array in a structure and return that structure.
Q4: How much memory does an array of 1000 structs with 56 bytes each use?
Approximately 56,000 bytes (56 KB) plus any alignment padding the compiler adds. Use sizeof(struct) * count for the exact answer.
Summary
- Arrays of structures model collections of records (like database tables)
- Elements are stored contiguously in memory for efficient access
- Sort with custom comparators (bubble sort or
qsort()) - Search with linear scan or binary search (if sorted)
- Use
malloc() for dynamic-sized struct arrays - Pass to functions as
struct Type arr[] or struct Type *arr