Reference: stdlib.h
Memory, conversions, random numbers, qsort, and exit.
6 minute read
Big idea
<stdlib.h> is the general utilities header: heap memory, converting text to numbers, random numbers, sorting and searching, and ending the program.
Memory
malloc
void *malloc(size_t bytes);
Reserves bytes bytes on the heap. Contents are garbage. Returns NULL if it can't. See malloc and calloc.
- Gotcha: it takes bytes, not items —
malloc(n * sizeof *p). Check forNULL. - Example:
int *a = malloc(n * sizeof *a);
calloc
void *calloc(size_t count, size_t size);
Reserves count × size bytes, all set to zero.
- Example:
int *tally = calloc(26, sizeof *tally);
realloc
void *realloc(void *p, size_t bytes);
Resizes a heap block, keeping its contents; may move it. realloc(NULL, n) is malloc(n). See free and realloc.
- Gotcha: on failure it returns
NULLand leaves the old block alone — assign to a temporary first, or you leak it. - Example:
int *t = realloc(a, cap * sizeof *t); if (t) a = t;
free
void free(void *p);
Gives a heap block back. free(NULL) does nothing.
- Gotcha: free exactly once, never use the memory afterwards, never free something that didn't come from
malloc/calloc/realloc. - Example:
free(a); a = NULL;
Text to numbers
strtol / strtoul / strtoll
long strtol(const char *s, char **end, int base);
Converts text to a long in the given base (10 for decimal, 16 for hex, 0 to auto-detect 0x). Sets *end to the first character it didn't use; sets errno to ERANGE if the number is too big. See Error Handling.
- Gotcha: it's the only family here that can report errors — check
end != sand*end == '\0'. - Example:
char *end; long v = strtol("42", &end, 10);
strtod
double strtod(const char *s, char **end);
The same, for decimals.
- Example:
double d = strtod("2.5e3", NULL);→ 2500
atoi / atol / atof
int atoi(const char *s);
double atof(const char *s);
Quick conversions with no error reporting: junk gives 0.
- Gotcha:
atoi("abc")andatoi("0")both return 0. Fine for tests, not for user input. - Example:
int n = atoi(argv[1]);
Integer maths
abs / labs / llabs
int abs(int x);
long labs(long x);
Absolute value of an integer. (fabs for doubles is in <math.h>.)
- Gotcha:
abs(INT_MIN)overflows — there's no positive version of the smallest int.
div
div_t div(int a, int b);
Quotient and remainder at once: .quot and .rem.
- Example:
div_t r = div(17, 5);→r.quot3,r.rem2
Random numbers
rand / srand
int rand(void);
void srand(unsigned seed);
rand returns 0 to RAND_MAX (at least 32767). srand seeds the sequence. See Math, Random Numbers, and Time.
- Gotcha: seed once —
srand(time(NULL))at the start ofmain. Not suitable for anything secret. - Example:
int die = rand() % 6 + 1;
Sorting and searching
qsort
void qsort(void *base, size_t count, size_t size,
int (*cmp)(const void *, const void *));
Sorts any array using your comparator. See Function Pointers and Callbacks.
- Gotcha: the comparator gets pointers to elements. Return negative / 0 / positive; avoid
a - b(overflow). - Example:
qsort(a, n, sizeof a[0], cmp_int);
bsearch
void *bsearch(const void *key, const void *base, size_t count, size_t size,
int (*cmp)(const void *, const void *));
Binary search in a sorted array, using the same kind of comparator. Returns a pointer to a match, or NULL.
- Example:
int *hit = bsearch(&target, a, n, sizeof a[0], cmp_int);
Ending the program and the environment
exit
void exit(int status);
Ends the program from anywhere, flushing open files. EXIT_SUCCESS (0) and EXIT_FAILURE are defined here.
- Example:
if (cfg == NULL) exit(EXIT_FAILURE);
getenv
char *getenv(const char *name);
Reads an environment variable; NULL if it isn't set.
- Example:
const char *home = getenv("HOME");
system
int system(const char *command);
Runs a shell command. Avoid it with any text that came from a user.
#include <stdio.h>
#include <stdlib.h>
int cmp_int(const void *pa, const void *pb) {
int a = *(const int *) pa, b = *(const int *) pb;
return (a > b) - (a < b);
}
int main(void) {
const char *words[] = {"40", "-7", "15", "8"};
int n = 4;
int *a = malloc(n * sizeof *a);
if (a == NULL) return EXIT_FAILURE;
for (int i = 0; i < n; i++) a[i] = (int) strtol(words[i], NULL, 10);
qsort(a, n, sizeof a[0], cmp_int);
for (int i = 0; i < n; i++) printf("%d ", a[i]);
printf("\n");
int key = 15;
int *hit = bsearch(&key, a, n, sizeof a[0], cmp_int);
printf("15 is at index %d\n", hit ? (int) (hit - a) : -1);
div_t r = div(17, 5);
printf("17 = 5*%d + %d, abs(-9) = %d\n", r.quot, r.rem, abs(-9));
free(a);
return EXIT_SUCCESS;
}output
-7 8 15 40
15 is at index 2
17 = 5*3 + 2, abs(-9) = 9Run and edit it in the app.
Which function lets you detect that "12abc" isn't a clean number?
Check yourself
What does realloc return if it fails?
What does bsearch need that qsort doesn't?