I recently did a quick study of the new features introduced in C++20, and I’d like to summarize what I’ve learned here.
Core Languages Enhancements
constinit & consteval & enhanced constexpr
The above three keywords enable code to be evaluated or initialized at compile time.
The main goal of these keywords, from my perspective, are shown as following:
- constinit
- ensure deterministic initialization of globals / statics at compile time, guaranteeing that all defined variables are accessed only after initialization, thereby improving code safety and predictability
- consteval & constexpr
- enforce execution exclusively at compile time, reducing runtime overhead by shifting work to compile time
template parameters in lambadas
auto print = []<typename T>(T value) {
std::cout << value << std::endl;
};
As shown in the code snippet above, templates are supported in lambda functions.
Concepts and Type Constrains
(This part introduces constraint support for templates, offering clearer and safer restrictions on template types. Since I’m not particularly interested in it, I’ll go ahead and skip it)
Ranges-based Programming
The Ranges library offers a modern interface for manipulating sequence data structure such as vector. It’s views component enables lazy evaluation without modifying the original data, resembling the Stream API in Java.
#include <iostream>
#include <vector>
#include <ranges>
#include <algorithm>
int main() {
std::vector<int> data = {10, 3, 6, 7, 4, 15, 8, 2, 9, 11, 12};
// 1. Filter even numbers
// 2. Square the even numbers
// 3. Copy the view into a vector to allow sorting
// 4. Sort the squared values in descending order
// 5. Take the top 5 elements
// 6. Output the results
// Compose views: filter + transform
auto even_squares_view = data
| std::views::filter([](int x) { return x % 2 == 0; })
| std::views::transform([](int x) { return x * x; });
// Copy view contents into a vector for sorting
std::vector<int> processed(even_squares_view.begin(), even_squares_view.end());
// Sort in descending order
std::ranges::sort(processed, std::greater<>());
// Take the top 5 elements
auto top5 = processed
| std::views::take(5);
// Output the results
for (int x : top5) {
std::cout << x << " ";
}
std::cout << "\n";
return 0;
}
Additionally, C++23 introduced the iota method, which provides a simple way to initialize sequence data structures.
std::vector<int> v(5);
std::ranges::iota(v, 42); // the result will be: {42, 43, 44, 45, 46}
Coroutines and Asynchronous Programming
(TODO)
Modules and Compilation Model
(TODO)
Standard Library Improvements
(TODO)