The Basics

  • Procedural Programming - ??
  • Read about the data types from cppreference

Arrays and Pointers

Arrays

Fundamental collection: contiguously allocated sequence of elements of same type.

char v[6];    // array of 6 characters: v[0] to v[5]
  • Size must be constant expression
  • Lower bound is 0

Pointers

char* p;              // pointer to character
char* p = &v[3];      // p points to v's fourth element
char x = *p;          // *p is the object that p points to
  • In declarations: [] means “array of”, * means “pointer to”
  • In expressions: prefix * means “contents of”, prefix & means “address of”

Visual representation:

v:  [v[0]][v[1]][v[2]][v[3]][v[4]][v[5]]
                     ↑
                      p points here

References

Reference = alias (alternative name) for an object. Like a pointer but without needing *.

int x = 10;
int* p = &x;    // Pointer: need *p to access value
int& r = x;     // Reference: r IS x
r = 20;         // Changes x to 20
  • No dereferencing needed to access value
  • Cannot be reseated (can’t refer to different object after init)

References as Function Arguments

Avoids copying expensive objects:

void sort(vector<double>& v);           // Reference - modifies original
void print(const vector<double>& v);    // const ref - read-only, no copy

Range-for with References

int v[] = {0, 1, 2, 3};
for (auto& x : v) {
    ++x;    // Modifies actual elements
}

Header Files

  • Header files (.h/.hpp) contain declarations - tell compiler what exists, not how
  • Source files (.cpp) contain definitions - the actual implementation
  • Used for: code reusability, separation of interface/implementation, single source of truth
// mymath.h (declaration)
int max(int a, int b);
// mymath.cpp (definition)
int max(int a, int b) { return (a > b) ? a : b; }
// main.cpp (usage)
#include "mymath.h"
int main() { int m = max(5, 3); }

Common standard headers: <iostream>, <vector>, <string>, <algorithm>

Generic Programming

  • Generic programming = write code that works with any data type without sacrificing performance
  • Templates - the mechanism for generic code
  • auto - compiler deduces type automatically, reduces verbosity, prevents copy-paste errors Example:
template<typename T>
T max(T a, T b) {
    return (a > b) ? a : b;
}
auto x = max(5, 3);        // x is int
auto y = max(3.14, 2.71); // y is double

const vs constexpr vs consteval

KeywordEvaluationUse Case
constCompile-time OR runtimeRead-only variables
constexprCompile-time (preferred), falls back to runtimeValues known at compile time
constevalMUST be compile-time (C++20)True compile-time computation
  • Compile-time: When compiler is running, before program executes
  • Runtime: When program is actually running

const

const int x = 5;        // Compile-time constant
const int y = rand();   // Runtime constant - set once, never changes

Just means “won’t change after initialization”

constexpr

constexpr int x = 5;           // Computed at compile time
constexpr int y = 10 * 20;     // Computed at compile time

Compiler TRIES to evaluate at compile time. Falls back to runtime if it can’t.

consteval (C++20)

consteval int square(int x) { return x * x; }  // MUST compile-time

Forces compile-time evaluation. Used for metaprogramming, compile-time validation.

When to use

  • const: Default for any variable that won’t change
  • constexpr: For values that SHOULD be computed at compile time (array sizes, template args)
  • consteval: When you NEED it to be compile-time

const Deep Dive

const Variables

const int x = 5;    // Can't change x after this

const References

void print(const vector<double>& v);  // Read-only, won't modify v

const Pointers (3 types)

int x = 5, y = 10;
 
// 1. Pointer to const - can't modify value through pointer
const int* p1 = &x;
// *p1 = 20;    // ERROR
p1 = &y;         // OK
 
// 2. Const pointer - can't change where pointer points
int* const p2 = &x;
*p2 = 20;        // OK
// p2 = &y;      // ERROR
 
// 3. Const pointer to const - can't do either
const int* const p3 = &x;
// *p3 = 20;     // ERROR
// p3 = &y;      // ERROR

Tip: Read right to left: const int* p = “p is pointer to int that is const”

const Methods (Class)

class Circle {
    double radius;
public:
    double area() const {  // Won't modify this object
        return 3.14 * radius * radius;
    }
};

See Also