I am getting confused with size_t
in C. I know that it is returned by the sizeof
operator. But what exactly is it? Is it a data type?
Let\'
size_t
is a type that can hold any array index.
Depending on the implementation, it can be any of:
unsigned char
unsigned short
unsigned int
unsigned long
unsigned long long
Here's how size_t
is defined in stddef.h
of my machine:
typedef unsigned long size_t;
The manpage for types.h says:
size_t shall be an unsigned integer type
From my understanding, size_t
is an unsigned
integer whose bit size is large enough to hold a pointer of the native architecture.
So:
sizeof(size_t) >= sizeof(void*)
size_t is unsigned integer data type. On systems using the GNU C Library, this will be unsigned int or unsigned long int. size_t is commonly used for array indexing and loop counting.
size_t or any unsigned type might be seen used as loop variable as loop variables are typically greater than or equal to 0.
When we use a size_t object, we have to make sure that in all the contexts it is used, including arithmetic, we want only non-negative values. For instance, following program would definitely give the unexpected result:
// C program to demonstrate that size_t or
// any unsigned int type should be used
// carefully when used in a loop
#include<stdio.h>
int main()
{
const size_t N = 10;
int a[N];
// This is fine
for (size_t n = 0; n < N; ++n)
a[n] = n;
// But reverse cycles are tricky for unsigned
// types as can lead to infinite loop
for (size_t n = N-1; n >= 0; --n)
printf("%d ", a[n]);
}
Output
Infinite loop and then segmentation fault
size_t
and int
are not interchangeable. For instance on 64-bit Linux size_t
is 64-bit in size (i.e. sizeof(void*)
) but int
is 32-bit.
Also note that size_t
is unsigned. If you need signed version then there is ssize_t
on some platforms and it would be more relevant to your example.
As a general rule I would suggest using int
for most general cases and only use size_t
/ssize_t
when there is a specific need for it (with mmap()
for example).