C Cheatsheet

Pointers, memory, structs, preprocessor, I/O & standard library

Language
Contents
โšก

Basics & Types

// Hello World
#include <stdio.h>

int main(void) {
    printf("Hello, World!\n");
    return 0;
}

// Data types
char   c = 'A';          // 1 byte
short  s = 32767;        // 2 bytes
int    i = 42;           // 4 bytes (typically)
long   l = 100000L;      // 4-8 bytes
float  f = 3.14f;        // 4 bytes
double d = 3.14159265;   // 8 bytes
unsigned int u = 42U;    // no negative values

// Type qualifiers
const int MAX = 100;     // read-only
volatile int reg;         // may change unexpectedly
static int count = 0;    // persists across calls

// Arrays
int arr[5] = {1, 2, 3, 4, 5};
int matrix[3][4];          // 2D array
int len = sizeof(arr) / sizeof(arr[0]);
๐Ÿ”—

Pointers & Memory

// Pointer basics
int x = 42;
int *p = &x;              // p holds address of x
printf("%d", *p);         // dereference โ†’ 42
*p = 100;                 // x is now 100

// Pointer arithmetic
int arr[] = {10, 20, 30};
int *ptr = arr;            // points to arr[0]
ptr++;                     // now points to arr[1]
*(ptr + 1)                 // arr[2] โ†’ 30

// Pointer to pointer
int **pp = &p;
**pp = 200;               // x is now 200

// Function pointers
int add(int a, int b) { return a + b; }
int (*fp)(int, int) = add;
fp(3, 4);                  // 7

// NULL pointer
int *null_ptr = NULL;
if (null_ptr != NULL) { /* safe to dereference */ }
๐Ÿ“

Strings

#include <string.h>

char s1[] = "Hello";           // mutable, stack
char *s2   = "Hello";           // pointer to literal (read-only!)
char s3[20];
strcpy(s3, "Hello");           // copy string

strlen(s1)                      // 5 (no null byte)
strcmp(s1, s2)                   // 0 if equal
strncmp(s1, s2, 3)              // compare first 3
strcat(s3, " World")            // concatenate
strncat(s3, "!!", 1)           // append n chars
strchr(s1, 'l')                // first occurrence
strstr(s1, "llo")              // substring search
sprintf(s3, "%s %d", "num", 5) // formatted print to string
snprintf(s3, 20, "%s", "safe")// bounds-safe version

// Character functions (<ctype.h>)
isalpha(c)  isdigit(c)  isspace(c)
toupper(c)  tolower(c)
๐Ÿ—๏ธ

Structs & Unions

// Struct
struct Point {
    int x;
    int y;
};
struct Point p1 = {10, 20};
p1.x = 30;

// Typedef
typedef struct {
    char name[50];
    int  age;
} Person;
Person p = {"Alice", 30};

// Pointer to struct
Person *pp = &p;
pp->age = 31;                // arrow operator

// Union (shared memory)
union Data {
    int    i;
    float  f;
    char   str[20];
};  // size = largest member

// Enum
enum Color { RED, GREEN, BLUE };
enum Color c = GREEN;          // GREEN = 1
โš™๏ธ

Preprocessor

#define PI 3.14159
#define MAX(a,b) ((a) > (b) ? (a) : (b))
#define SQUARE(x) ((x) * (x))

#ifdef DEBUG
    printf("Debug mode\n");
#endif

#ifndef HEADER_H
#define HEADER_H
// header content (include guard)
#endif

#if defined(__linux__)
    // Linux-specific code
#elif defined(__APPLE__)
    // macOS-specific code
#else
    // fallback
#endif

#pragma once              // modern include guard
__FILE__  __LINE__  __DATE__  __TIME__  // built-in macros
๐Ÿ“‚

File I/O

#include <stdio.h>

// Open / Close
FILE *fp = fopen("data.txt", "r");   // r, w, a, rb, wb, r+
if (!fp) { perror("Error"); return 1; }
fclose(fp);

// Read
char buf[256];
fgets(buf, 256, fp);             // read line
fscanf(fp, "%d %s", &num, str);  // formatted read
fread(buf, 1, 256, fp);          // binary read
int ch = fgetc(fp);               // read char

// Write
fprintf(fp, "Name: %s\n", name);
fputs("Hello\n", fp);
fwrite(data, 1, size, fp);       // binary write
fputc('A', fp);

// Position
fseek(fp, 0, SEEK_SET);          // beginning
fseek(fp, 0, SEEK_END);          // end
long pos = ftell(fp);
rewind(fp);

// Check
feof(fp)     // end of file?
ferror(fp)   // error occurred?
๐Ÿ“š

Standard Library

#include <stdlib.h>
#include <math.h>

// stdlib.h
atoi("42")       // string โ†’ int
atof("3.14")     // string โ†’ double
strtol(s, NULL, 10)  // safer string โ†’ long
abs(-5)           // 5
rand() % 100      // random 0-99
srand(time(NULL))  // seed random
exit(0)            // terminate program
system("ls")       // run shell command

qsort(arr, n, sizeof(int), compare_fn);
bsearch(&key, arr, n, sizeof(int), compare_fn);

// math.h (link with -lm)
sqrt(16.0)    // 4.0
pow(2, 10)    // 1024.0
ceil(3.2)     // 4.0
floor(3.8)    // 3.0
fabs(-3.5)    // 3.5
log(2.718)    // ~1.0 (natural)
log10(100)    // 2.0
sin(x) cos(x) tan(x) atan2(y, x)
๐Ÿง 

Dynamic Memory

#include <stdlib.h>

// malloc โ€” allocate uninitialized memory
int *arr = (int *)malloc(10 * sizeof(int));
if (!arr) { /* allocation failed */ }

// calloc โ€” allocate zero-initialized
int *arr2 = (int *)calloc(10, sizeof(int));

// realloc โ€” resize
arr = (int *)realloc(arr, 20 * sizeof(int));

// free โ€” release memory
free(arr);
arr = NULL;   // avoid dangling pointer

// Common mistakes
// โœ— Use after free (dangling pointer)
// โœ— Double free
// โœ— Memory leak (forgot free)
// โœ— Buffer overflow (write past allocation)
// โœ“ Always check malloc return value
// โœ“ Always free what you malloc
// โœ“ Set pointer to NULL after free
๐Ÿ”ข

Bitwise Ops

// Operators
a & b      // AND    0b1100 & 0b1010 = 0b1000
a | b      // OR     0b1100 | 0b1010 = 0b1110
a ^ b      // XOR    0b1100 ^ 0b1010 = 0b0110
~a         // NOT    ~0b1100 = 0b0011 (inverted)
a << n     // left shift  (ร— 2^n)
a >> n     // right shift (รท 2^n)

// Common tricks
x & 1              // check if odd
x & (x - 1)        // clear lowest set bit
x | (x - 1)        // set all bits after lowest
1 << n              // nth bit mask
x | (1 << n)       // set nth bit
x & ~(1 << n)      // clear nth bit
x ^ (1 << n)       // toggle nth bit
(x >> n) & 1       // check nth bit
๐Ÿ”ง

Common Patterns

// Swap without temp
a ^= b; b ^= a; a ^= b;

// Linked list node
typedef struct Node {
    int data;
    struct Node *next;
} Node;

// qsort comparator
int cmp(const void *a, const void *b) {
    return (*(int*)a - *(int*)b);
}
qsort(arr, n, sizeof(int), cmp);

// Error handling pattern
int process() {
    FILE *fp = fopen("f.txt", "r");
    if (!fp) goto err_file;
    char *buf = malloc(1024);
    if (!buf) goto err_buf;
    // ... work ...
    free(buf);
err_buf:
    fclose(fp);
err_file:
    return -1;
}

// Compile: gcc -Wall -Wextra -O2 -o prog main.c
// Debug:   gcc -g -fsanitize=address -o prog main.c