Arrays
Many values, one nameAn array stores many values of the same type in one row of memory, and you reach each one by its index. In the lab below you watch the cells being filled, see what really happens when you write past the end, and run the classic array loops: sum and maximum, linear search and reversing.
- int a[5]five ints side by side
- a[0] … a[4]indexes start at 0
- a[5]is past the end — C does not check
Ready
Keyboard: ← → step · Space play / pause · R reset · Esc exit classroom mode
The ideas behind the lab
Exactly what you watched happen, in plain steps.
One name, many cells
An array is a fixed number of variables of the same type, stored next to each other in memory. The size is fixed when it is declared. Each element is reached with an index in square brackets: the first is [0], the last is [size − 1]. Because the cells are side by side, the address of a[i] is simply start + i × the size of one element.
int a[5]; // 5 ints, garbage values
int b[5] = {10, 20, 30}; // 10 20 30 0 0
int c[] = {4, 7, 1}; // size counted: 3
int d[5] = {0}; // all zeros
b[1] = 99; // write (2nd element)
printf("%d", b[0]); // read (1st element)
int n = sizeof b / sizeof b[0]; // 5 elements
| Element | Value | Address | Offset |
|---|---|---|---|
| a[0] | 10 | 0x1000 | 0 × 4 = 0 bytes |
| a[1] | 20 | 0x1004 | 1 × 4 = 4 bytes |
| a[2] | 30 | 0x1008 | 2 × 4 = 8 bytes |
| a[3] | 0 | 0x100c | 3 × 4 = 12 bytes |
| a[4] | 0 | 0x1010 | 4 × 4 = 16 bytes |
| a[5] | — not part of a — | 0x1014 | out of bounds! |
Declaring and initialising
- type name[size]; — the size must be a positive whole number.
- Values in { } fill the cells from the start; missing ones become 0.
- With an initialiser list you may leave the size out: int c[] = {4, 7, 1};
- Without any initialiser, a local array holds garbage.
- An array cannot be assigned as a whole: b = a; is an error — copy element by element.
Indexes
- The first index is 0, the last is size − 1.
- The index can be any int expression: a[i], a[i + 1], a[n - 1].
- C does NOT check the index: a[5] in an int a[5] reads or writes someone else's memory.
- Out-of-bounds access is undefined behaviour: wrong values, changed variables or a crash.
- Loop with i = 0; i < size — never i <= size.
Classic array loops
- Traversal: for (i = 0; i < n; i++) visits every element once.
- Sum / average: an accumulator; divide by n as a double.
- Max / min: start with a[0], then compare every element.
- Linear search: compare one by one, break at the first match, -1 if none.
- Reverse: swap a[i] and a[j] while i < j, moving both towards the middle.
Average marks and how many are above it
Every line, explained.
#include <stdio.h>
#define N 5
The size in one place: change it here only.
int main(void)
{
int marks[N] = {72, 85, 60, 91, 78};
int sum = 0;
for (int i = 0; i < N; i++)
i = 0, 1, 2, 3, 4 — every valid index.
sum += marks[i];
sum = 386
double avg = (double) sum / N;
The cast avoids integer division.
printf("average %.1f\n", avg);
Prints average 77.2
int above = 0;
for (int i = 0; i < N; i++)
A second pass over the same array.
if (marks[i] > avg) above++;
85, 91 and 78
printf("%d above average\n", above);
Prints 3 above average
printf("%zu bytes\n", sizeof marks);
Prints 20 bytes (5 × 4)
return 0;
}
Spot the bug
Mistakes almost every beginner makes — and how to fix them.
Looping one element too far
for (i = 0; i <= 5; i++) a[i] = 0; // a has 5 elements
for (i = 0; i < 5; i++) a[i] = 0;
a[5] does not exist. Writing it changes other memory — no error message, just strange bugs.
Starting at index 1
for (i = 1; i <= n; i++)
sum += a[i];
for (i = 0; i < n; i++)
sum += a[i];
This skips a[0] and reads a[n], which is out of bounds.
Copying an array with =
int a[3] = {1, 2, 3}, b[3];
b = a; // error
for (i = 0; i < 3; i++)
b[i] = a[i];
An array name is not a variable you can assign to. Copy the elements one by one (or use memcpy).
Using an uninitialised array
int count[10]; count[3]++; // garbage + 1
int count[10] = {0};
count[3]++;
A local array without an initialiser holds whatever was in memory. = {0} sets every element to 0.
Starting the maximum at 0
int max = 0; // wrong for {-5, -2, -9}
int max = a[0];
If all values are negative, 0 is never beaten and max stays 0 — a value that is not even in the array.
Check your understanding
Answer each question — you will see the explanation straight away.
int a[6]; — what is the last valid index?
Indexes run from 0 to size − 1.
int a[4] = {3, 8}; — what is a[3]?
Missing values in an initialiser list become 0.
int a[] = {5, 1, 4}; — how many bytes is sizeof a (4-byte int)?
3 elements × 4 bytes.
What does C do when you write a[10] in an int a[5]?
C never checks indexes at run time.
int a[] = {2, 4, 6}; int s = 0; for (int i = 0; i < 3; i++) s += a[i]; — s is?
2 + 4 + 6 = 12.
Arrays quiz
Test yourself: 10 questions, 70% to pass. Create a free account to take the quiz, save your progress and work towards the certificate.