C++ MASTERY

Complete Developer's Guide & Vocabulary

C++ Fundamentals

Variables & Types

Strong typing system with compile-time type checking

int age = 25; // 32-bit integer double pi = 3.14159; // double precision bool isActive = true; // boolean char grade = 'A'; // single character auto result = 42; // type deduction

Functions & Overloading

Function overloading based on parameter types

int add(int a, int b) { return a + b; } double add(double a, double b) { return a + b; } // Compiler chooses based on arguments int result1 = add(5, 3); // calls int version double result2 = add(5.5, 3.2); // calls double version

References vs Pointers

Two ways to indirectly access memory

int x = 10; int& ref = x; // reference (alias) int* ptr = &x; // pointer (address) ref = 20; // changes x to 20 *ptr = 30; // changes x to 30 // References can't be reassigned // Pointers can point to different objects

Dev Speak: Basic Concepts

"Always prefer references over pointers when you don't need pointer arithmetic or reassignment."
"Use auto for complex type declarations, but not when it hurts readability."
"Function overloading is resolved at compile time - it's not runtime polymorphism."

Object-Oriented Programming

Classes & Encapsulation

Data hiding and interface design

class BankAccount { private: double balance; std::string accountNumber; public: BankAccount(const std::string& accNum) : accountNumber(accNum), balance(0.0) {} void deposit(double amount) { if (amount > 0) balance += amount; } double getBalance() const { return balance; } };

Inheritance & Polymorphism

Code reuse and runtime behavior selection

class Shape { public: virtual double area() const = 0; // pure virtual virtual ~Shape() = default; // virtual destructor }; class Circle : public Shape { private: double radius; public: Circle(double r) : radius(r) {} double area() const override { return 3.14159 * radius * radius; } };

Constructor Types

Different ways to initialize objects

class MyClass { public: // Default constructor MyClass() = default; // Parameterized constructor MyClass(int value) : data(value) {} // Copy constructor MyClass(const MyClass& other) : data(other.data) {} // Move constructor MyClass(MyClass&& other) noexcept : data(std::move(other.data)) {} private: int data; };

The Big Five/Six

Essential special member functions every C++ dev should know:

  • Destructor - Clean up resources
  • Copy Constructor - Deep copy semantics
  • Copy Assignment - Assignment operator overload
  • Move Constructor - Efficient resource transfer
  • Move Assignment - Move assignment operator
  • Default Constructor - Zero-argument initialization

Memory Management

Stack vs Heap

Understanding memory allocation strategies

// Stack allocation - automatic cleanup void stackExample() { int localVar = 42; // on stack MyClass obj(10); // on stack } // automatic destruction here // Heap allocation - manual management void heapExample() { int* ptr = new int(42); // on heap // ... use ptr ... delete ptr; // manual cleanup }

Smart Pointers

RAII-based automatic memory management

// unique_ptr - exclusive ownership std::unique_ptr<int> ptr1 = std::make_unique<int>(42); // shared_ptr - shared ownership std::shared_ptr<int> ptr2 = std::make_shared<int>(42); std::shared_ptr<int> ptr3 = ptr2; // ref count = 2 // weak_ptr - non-owning reference std::weak_ptr<int> weak = ptr2;

RAII Pattern

Resource Acquisition Is Initialization

class FileHandler { private: std::ifstream file; public: FileHandler(const std::string& filename) : file(filename) { if (!file.is_open()) { throw std::runtime_error("Failed to open file"); } } // Destructor automatically closes file ~FileHandler() { if (file.is_open()) file.close(); } };

Dev Speak: Memory Management

"If you're using raw new/delete in modern C++, you're probably doing it wrong."
"RAII isn't just about memory - it's about any resource that needs cleanup."
"Smart pointers express ownership semantics in the type system."

Templates & Generic Programming

Function Templates

Generic functions that work with any type

template<typename T> T max(const T& a, const T& b) { return (a > b) ? a : b; } // Template specialization template<> const char* max(const char* const& a, const char* const& b) { return (strcmp(a, b) > 0) ? a : b; }

Class Templates

Generic classes for type-safe containers

template<typename T> class Stack { private: std::vector<T> elements; public: void push(const T& item) { elements.push_back(item); } T pop() { if (elements.empty()) { throw std::runtime_error("Stack is empty"); } T top = elements.back(); elements.pop_back(); return top; } };

Template Metaprogramming

Compile-time computation and type manipulation

// SFINAE - Substitution Failure Is Not An Error template<typename T> typename std::enable_if<std::is_integral<T>::value, T>::type process(T value) { return value * 2; // only for integral types } // Concepts (C++20) template<typename T> concept Numeric = std::is_arithmetic_v<T>; template<Numeric T> T square(T x) { return x * x; }

Standard Template Library (STL)

Containers

Data structures for different use cases

// Sequence containers std::vector<int> vec = {1, 2, 3}; // dynamic array std::deque<int> deq = {1, 2, 3}; // double-ended queue std::list<int> lst = {1, 2, 3}; // doubly linked list // Associative containers std::map<std::string, int> ages; // ordered key-value std::unordered_map<std::string, int> fast_ages; // hash table std::set<int> unique_nums; // unique sorted elements

Algorithms

Generic algorithms that work with iterators

std::vector<int> numbers = {3, 1, 4, 1, 5}; // Sorting and searching std::sort(numbers.begin(), numbers.end()); auto it = std::find(numbers.begin(), numbers.end(), 4); // Transformations std::vector<int> squared(numbers.size()); std::transform(numbers.begin(), numbers.end(), squared.begin(), [](int x) { return x * x; });

Iterators

Generalized pointers for container traversal

std::vector<int> vec = {1, 2, 3, 4, 5}; // Different iterator types auto forward_it = vec.begin(); // forward iterator auto reverse_it = vec.rbegin(); // reverse iterator auto const_it = vec.cbegin(); // const iterator // Range-based for loop (syntactic sugar) for (const auto& element : vec) { std::cout << element << " "; }

Modern C++ Features

Lambda Expressions

Anonymous functions for functional programming

// Basic lambda auto add = [](int a, int b) { return a + b; }; // Capture by value and reference int multiplier = 10; auto scale = [multiplier](int x) { return x * multiplier; }; auto modify = [&multiplier](int x) { multiplier += x; }; // Generic lambda (C++14) auto generic = [](auto x, auto y) { return x + y; }; // Used with algorithms std::sort(vec.begin(), vec.end(), [](int a, int b) { return a > b; });

Move Semantics

Efficient resource transfer without copying

class MyString { private: char* data; size_t size; public: // Move constructor MyString(MyString&& other) noexcept : data(other.data), size(other.size) { other.data = nullptr; // leave other in valid state other.size = 0; } // Move assignment MyString& operator=(MyString&& other) noexcept { if (this != &other) { delete[] data; data = other.data; size = other.size; other.data = nullptr; other.size = 0; } return *this; } };

Perfect Forwarding

Preserving value categories in template functions

template<typename T, typename... Args> std::unique_ptr<T> make_unique(Args&&... args) { return std::unique_ptr<T>( new T(std::forward<Args>(args)...) ); } // Universal reference with perfect forwarding template<typename T> void wrapper(T&& arg) { some_function(std::forward<T>(arg)); }

C++ Developer Vocabulary

RAII
Resource Acquisition Is Initialization - tie resource lifetime to object lifetime
"RAII is the foundation of exception-safe C++ code"
PIMPL
Pointer to Implementation - hide implementation details in private pointer
"PIMPL reduces compilation dependencies and hides implementation details"
SFINAE
Substitution Failure Is Not An Error - template metaprogramming technique
"SFINAE lets you enable/disable template instantiations based on type properties"
ODR
One Definition Rule - each entity can have only one definition in program
"ODR violations are undefined behavior and hard to debug"
ADL
Argument-Dependent Lookup - compiler looks for functions in namespaces of arguments
"ADL is why you can write 'std::cout << x' without qualifying operator<<"
CRTP
Curiously Recurring Template Pattern - template inherits from instantiation of itself
"CRTP gives you static polymorphism without virtual function overhead"
UB
Undefined Behavior - code that can do anything, compiler makes no guarantees
"Undefined behavior isn't just unpredictable - it can break your entire program"
ABI
Application Binary Interface - low-level interface between compiled code modules
"Breaking ABI means recompiling everything that links against your library"
POD
Plain Old Data - C-compatible data types with trivial construction/destruction
"POD types can be memcpy'd safely and work with C APIs"
NRVO
Named Return Value Optimization - compiler eliminates unnecessary copies
"NRVO means returning large objects by value can be zero-cost"
TMP
Template Metaprogramming - computation at compile time using templates
"TMP moves runtime costs to compile time, but can make compilation slow"
Tag Dispatch
Overload resolution technique using empty types as discriminators
"Tag dispatch is cleaner than SFINAE for simple template overloading"

Things C++ Devs Actually Say

  • "Don't optimize prematurely, but design for performance"
  • "If it compiles, ship it" (just kidding - write tests!)
  • "Templates are compile-time duck typing"
  • "When in doubt, use const"
  • "RAII or die trying"
  • "Zero-cost abstractions are the C++ way"
  • "You don't pay for what you don't use"
  • "Trust the optimizer, but verify with profiling"
  • "Prefer composition over inheritance"
  • "Make interfaces easy to use correctly and hard to use incorrectly"

Quick Reference Cheat Sheet

Memory

// Smart pointers std::make_unique<T>(args...) // unique ownership std::make_shared<T>(args...) // shared ownership std::weak_ptr<T> // non-owning reference // Casts static_cast<T>(expr) // compile-time cast dynamic_cast<T>(expr) // runtime polymorphic cast const_cast<T>(expr) // remove const reinterpret_cast<T>(expr) // low-level cast

Common Patterns

// Range-based for for (const auto& item : container) { } // Structured bindings (C++17) auto [key, value] = map_pair; // If with initializer (C++17) if (auto result = find(x); result != end()) { } // Uniform initialization std::vector<int> v{1, 2, 3};