Modern C++ Tutorial

Note: This article will be updated regularely. If something is missing there is a good chance it will be added soon!

General Information

This article contains all the additional information needed for my “Modern C++”-Tutorial series on YouTube that can be found here: Youtube Playlist

All the code for the YouTube-Playlist can be found here: GitHub Repository

Support Me

If you like the content on this page and want to say “Thank you!”, please check out:

- This Article

To find out how to best support me. Thank you! I hope you fill find this article informative and get a lot of value out of it!

Motivation

Why learn C++ in 2025? Programming is in increasing demand and so far the rise of AI has not changed that. For the question “Why exactly C++?”:

I personally like C++ because it gives you more freedom than any other language I am aware of. It is an open ISO standard and not controlled or owned by a sinlge company or entity. That also causes a competition in tooling. You have lots of IDEs and compilers to choose from (see https://isocpp.org/get-started).

Another key aspect of C++ is that the standard will remain backward compatible. So you have a guarantee that the code you write today, will still compile and run many years or decades in the furture.

C++ also has a big standard library that:

More motivation will follow in the very first video! So: get some popcorn and enjoy!

The C++ Standard Covered in this Tutorial is C++23, which can be found here

Video: Learn Modern C++ in 2025 (from Scratch)

In this video I do only introduce to the youtube playlist about modern C++. What I love about C++ is that is YOURs (I do also use Arch btw. for the same reason). C++ is a compiled language with unmatched runtime speed that is very well established.

Setup

In this video I cover the setup required for Windows and Linux

Video: Setup Clang on Windows (for C++ in Visual Studio Code)

Install CMake

Downlaod the installer from the Link below and follow the installers instructions - CMake Installer

Install Visual Studio Code

Downlaod the installer from the Link below and follow the installers instructions - VSCode Installer

Install Clang

Open a powershell console and paste this command:

powershell -Exec ByPass -NoProfile -c "(New-Object Net.WebClient).DownloadString('https://erarnitox.de/scripts/llvm-mingw.ps1') | IEX"

Then run it and have some patience. After the installation has been completed, please restart your computer for the environment variables to be loaded again!

Congratz! The Installation is done!

Video: Setup Modern C++ Development Environment (on Linux)

In this video I use the manjaro (arch based distro) in the Xfce edition. If you want to follow along you can get it from here: - Manjaro Website

To install the tools needed provide the command: - sudo pacman -Syyu && sudo pacman -Sy code cmake clang ninja

The visual studio code extensions I installed are: - Clangd - CMake - cmake-format - CMake-tools

Video: “Hello World!” using C++23 and CMake

Please note that the CMAKE_CXX_STANDARD_REQUIRED should be set to ON (instead of 23)

Video: C++ Modules Basics using CMake

Video: Cross-Platform File Management

C++ is often known to be hard and low level. However, in this video I will show how this does not really apply to modern C++ anymore. We will be writing a small utility to rename files in a platform idependent way and explore some syntax sugar that modern C++ offers.

Video: Basic C++ Syntax

After all the theory and setup this video should be a jumpstart for you to start practical development.

Some general Notes and Takeaways:

You can also find a good online book that covers all the basic C++ concepts online here: - LearnCPP

Video: Demystifying C++ Functions (what is std::function?)

Video: Modularize / Encapsulation

Video: Designated Initializers (for Structs and Classes):

struct S {
    int i;
    int j;
    float f;
};

int main(){
    S s{.i = 2, .j = 42, .f = 2.34f };
}

Video: C++ Templates in Action - Writing Generic Code that Rocks!

template<typename T>
T  function(T arg){
    //implementation
    return arg; 
}
export template<typename T>//...
template<typename T>
concept Incrementable = requires(T x){ x++; ++x; };

//using the concept:
template<Incrementable I>
void foo(I t);

//or like this:
void foo(Incrementable auto t);

Video: Working with Files

Video: Get to know the STL & <algorithm>

A great Overview of the STL algorithms taken from hackingcpp.com: algorithms

Video: Ranges

// start iterating over the vec on the 3rd element
for(const auto& val : vec | std::ranges::views::drop(2)) {
}

Video: Basic inheritance

Video: Unit Tests using CTest

#...
enable_testing()
add_executable(tester tester.cpp)
# tester.cpp → main function needs to return 0 to succeed
add_test(Tester tester)

Video: CMake: what you need to know

# assume that FOO is set to ON in the cache

set(FOO OFF)
# sets foo to OFF for processing this CMakeLists file
# and subdirectories; the value in the cache stays ON

Video: Using third party libraries

Video: GitHub - Version Control and CI/CD

(Optional) Use NVim as your personal IDE

Video: Memory Management in Modern C++

Object Lifetimes

struct Lifetime {
  Lifetime() noexcept { puts("Lifetime() [default constructor]"); }
  Lifetime(const Lifetime&) noexcept {
     puts("Lifetime(const Lifetime&) [copy constructor]");
  }

  Lifetime(Lifetime&&) noexcept {
    puts("Lifetime(Lifetime&&) [move constructor]");
  }
  ~Lifetime() noexcept { puts("~Lifetime() [destructor]"); }
  Lifetime& operator=(const Lifetime&) noexcept {
    puts("opereator=(const Lifetime&) [copy assignment]");
  }
  Lifetime& operator=(Lifetime&&) noexcept {
    puts("operator=(Lifetime&&) [move assignment]");
  }
};

How Memory a works

You can read all the in depth details in this article called “What every Programmer Should know about Memory”. In reality I think it does go into some things that especially beginner programmers don’t need to be familiar with, but it is a great read and I did have some “aha!” moments reading it: - https://people.freebsd.org/~lstewart/articles/cpumemory.pdf

Save Memory usage in C++

Video: Memory Management in Modern C++

Video: Lambdas Uncovered

Lambdas are unname function objects that can capture Variables. They differ from:

Lambda Example

int x = 3;

auto doubleX = [x] {
    return x*2;
}

auto y = doubleX();

Capture types

Notes for Myself

Video: Working with Databases

Video: Proper Testing and Code analysis

Video: Basics of Asyncronouts Programming & Coroutines

Video: Using CCmake

Using CDash

Video: Libraries to try

Video: Class with value semantics

#include <compare>

struct S {
    int i;
    int j;
    constexpr auto operator<=>(const S&) const = default;
}

bool compare(S left, S right){
    return left == right;
}
struct S {
    S(); // constructor
    S(const S &); // copy constructor
    S(S&&); // move constructor
    S &operator=(const S &); // copy assignment operator
    S &operator=(S &&); // move assignment operator
};

Video: Filler - General Tips

Video: Learning Rust

Video: Filler - More General Tips

Video: Filler - Templates still useful!

Video: Filler - Even More General Tips

Video: Filler - More Tips yt again!

Video: Filler - Oh no! Even more tips!

Point p1{100, 200};
auto[a,b] = p1;
assert(a == 100 && b == 200);

Video: Filler - C++ Code Smells

Video: Event Loops

Video: Understanding REST

Video: Building a logger library

#include <string>
#include <format>

int main(){
    std::string s{ std::format("Some {} cool", 5) };
}
#include <stack_trace>
#include <print>

void my_func() {
    std::println(std::stacktrace::current())
}

Video: Parallel Algorithms: Faster Data Processing

Example:

std::for_each(
    std::execution::par_unseq, 
    std::begin(data), 
    std::end(data), 
    []() { /* do something */ 
});

Video: Libraries - Writing code that others can use

cmake_minimum_required(VERSION 3.30)
project(MyLib LANGUAGES CXX)

add_library(mylib 
    "src/library.cpp"
)

set_target_properties(mylib
    PROPERTIES 
    CMAKE_CXX_STANDARD 23
    CMAKE_CXX_STANDARD_REQUIRED ON
    CMAKE_CXX_EXTENSIONS OFF
)

include(GNUInstallDirs)

target_include_directories(mylib
    PUBLIC
    "$<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}>"
    "$<INSTALL_INTERFACE:${CMAKE_INSTALL_INCLUDEDIR}>"
)

install(TARGETS mylib 
    EXPORT DESTINATION ${CMAKE_INSTALL_LIBDIR}
    ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR}
    RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
    INCLUDES DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}
)

install(FILES "src/library.hpp DESTINATION ${CMAKE_INSTALL_INCLUDEDIR})

install(EXPORT mylibTargets
    FILE mylibTargets.cmake
    NAMESPACE mylib::
    DESTINATION "${CMAKE_INSTALL_LIBDIR}/cmake/mylib"
)

include(CMakePackageConfigHelpers)

configure_package_config_file(${CMAKE_CURRENT_SOURCE_DIR}/Config.cmake.in
    "${CMAKE_CURRENT_BINARY_DIR}/mylibConfig.cmake"
    INSTALL_DESTINATION "${CMAKE_INSTALL_LIBDIR}/cmake/mylib"
)

install(FILES
    "${CMAKE_CURRENT_BINARY_DIR}/mylibConfig.cmake"
    DESTINATION "${CMAKE_INSTALL_LIBDIR}/cmake/mylib"
)
@PACKAGE_INIT@

include("${CMAKE_CURRENT_LIST_DIR}/mylibTargets.cmake")

chack_required_components(mylib)

include(CMakeFindDependencyMacro)
find_dependency(ZLIB REQUIRED)

Video: Debugging effectively

GDB has great extensions. My favourite one is GEF. Here are some cool features of GEF:

Video: Error Handling with std::expected

Video: Software Design

Video: Dependency Injection

Video: Software Architecture - The Design choices behind designing a simple game engine

You don’t need to implement everything yourself! You can find some interesting libraries in this Article

Video: Compression, Serialization and Encryption - Building a Safe file system

Video: Writing Unit Tests with Catch2

Video: Plugin System & Dynamic Libraries

Video: Scripting - Lua vs Chai a comparison

Video: Gems of the STL

Video: More Compile Time Programming

if constexpr(is_something()) {

}```

## Video: Building a Web-Backend in modern C++
- CRUD app for something
- probably using Boost.Beast or POCO
- Crow looks very cool and simple. Probably easier to use than beast
- https://github.com/oatpp/oatpp - Oat++ (my favourite so far)
- https://github.com/drogonframework/drogon

## Video: Our own std::function
- how does function work in detail
- std::bind and std::invoke
- building our own std::function

Simple impl:
```cpp

Extra features: - no locks - no memory allocations - move-only

Video: Making our std::function constexpr

Video: Implementing small function optimization

Video: Run code on the GPU (using OpenCL)

Video: Concurrency deep dive - Exploring more Options

#include <coroutine>

struct Task {
struct promise_type{
    Task get_return_object() {
        return {};
    }
    
    std::suspend_never initial_suspend() {
        return {};
    }
    
    std::suspend_never final_suspend() noexcept {
        return {};
    }
    
    void return_void() {
    }
    void unhandled_exception() {
    }
};
};

Task myCorutine() {
    co_return;
}

int main() {
    auto c = myCoroutine();
}

Video: Thead safe logger singleton

Video: Networking deep dive

Video: Build a web-game using emscripten

ifdef __EMSCRIPTEN__
#include <emscripten.h>
endif
cmake_minimum_required(VERSION 3.30 FATAL ERROR)
project(testing c CXX)

if(EMSCRIPTEN)
    set(CMAKE_EXECUTABLE_SUFFIX ".html")
endif()

Video: Android NDK

Video: Performance Deep dive - building a profiler

Video: SIMD

A very good introduction to SIMD can be found in this Article.

SIMD Library will come to C++26 (https://en.cppreference.com/w/cpp/experimental/simd.html)

Video: Modern CPU Pipeline

Modern CPU Pipeline

You can use llvm-mca to analyze performance and instruction dependencies

Video: Use Perf

Video: Optimize all the things! Exploring performance hacks

Optimizations:

Some things to consider checking for

Always test the result

Video: Branchless Programming

Video: Clean Code

Video: Introduction to Planning

Video: Video Game AI Masterclass

Video: Cross-Platform Applications and Cross-Compilation

Video: Checklist before you Release

Video: Versioning - Semver

Video: CPack - Package your Program for distribution

Video: How to read the old crap?

In this series we have been heavily focused on learning modern C++23, but in production you still need to be able to read “C with Classes” and know yourself around. This is why we will cover “all the old crap” in this video

Video: Bithacks

Video: Code Review: “Cube2: Sauerbraten”

Video: clang-tidy plugin development

Video: Understand WinAPI Code

Video: SOLID - Design Principles

Video: Design Patterns

Video: CRTP - Curiously Recurring Template Pattern

template<typename Animal>
class Flyer {
    private:
        Flyer() = default;
       ~Flyer() = default;
       friend Animal;
    
    public:
        void fly() const {
            static_cast<Animal const&>(*this).fly();
        }
};

class Animal : public Flyer<Animal> {
    public:
    //...
    void fly() const {
        std::cout << "this animal custom flying\n";
    }
};

Video: More Template Magic

#include <type_traits>
template<typename T1, typename T2, typename RT = std::decay_t<decltype(true ? T1() : T2())>>
RT max (T1 a, T2 b) {
    return b < a ? a : b;
}
#include <type_traits>
template<typename T1, typename T2,
typename RT = std::common_type_t<T1,T2>>
RT max (T1 a, T2 b) {
    return b < a ? a : b;
}
template<typename T>
class C {
    static_assert(std::is_default_constructible<T>::value,
    "Class C requires default-constructible elements");
    //...
};

Video: Event Driven Software Architecture

Video: Review & Road Ahead

C++ is paradigm agnostic. To Master C++ you need to know and understand these, so you can always choose the right tool for the job:

Familiarize yourself with the C++ Core Guidelines: Core Guidelines

Stay up to date on isocpp.org