Created
August 1, 2020 15:36
-
-
Save crcrpar/a4492dfc1be6624b2aed301a00101640 to your computer and use it in GitHub Desktop.
Some epitome-ish code snippets from CppCon 2018: Nicolai Josuttis "The Nightmare of Initialization in C++"
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// https://youtu.be/7DTlWPgX6zs | |
// x86-64 Clang 9 | |
// opts: either `-std=c++17 --pedantic-errors` or `-std=c++14 --pedantic-errors` | |
#include <vector> | |
#include <string> | |
#include <atomic> | |
long long getLongInt(); | |
struct C{}; | |
struct C getC(); | |
struct BaseData { | |
std::string name; | |
double value; | |
}; | |
struct Data : BaseData { | |
bool used; | |
}; | |
int main() { | |
int i1; | |
int i2 = 42; | |
int i3(42); | |
int i4 = int(); | |
int i5{42}; | |
int i6 = {42}; | |
int i7{}; | |
int i8 = {}; | |
auto i9 = 42; | |
auto i10{42}; // inits int with 42 | |
auto i11 = {42}; // inits std::initializer_list<int> with 42 | |
auto i12 = int{42}; | |
int i13(); | |
int i14(7, 9); | |
int i15 = (7, 9); | |
int i16 = int(7, 9); | |
auto i17(7, 9); | |
auto i18 = (7, 9); | |
auto i19 = int(7, 9); | |
using namespace std::literals; | |
auto x = "42"s; | |
std::atomic<int> a{9}; | |
auto a1 = std::atomic<int>{9}; // fixed in C++17 | |
std::array<int, 5> r{}; | |
auto r1 = std::array{}; // expensive till C++17 | |
long long ll{getLongInt()}; | |
auto ll1 = long long {getLongInt()}; | |
auto ll2 = int64_t(getLongInt()); | |
auto ll3 = static_cast<long long>(getLongInt()); | |
const C & r = getC(); | |
auto r1 = static_cast<const C&>(getC()); | |
auto & r = static_cast<const C&>(getC()); | |
auto && r = static_cast<const C&>(getC()); | |
// `auto` decays: | |
// - Raw arrays convert to pointers | |
// - Functions convert to function pointers | |
// - Top-level references are removed | |
// - Top-level `const/volatile` qualifiers are removed | |
// as passing arguments by value | |
int i = 42; | |
const int & r = i; // `r` has type `const int &` and refers to `i` | |
auto v = r; // `v` has type `int` and is a new object; | |
const int arr[4] = {1, 2, 3, 4}; | |
auto a = arr; // `a` has type `const int *` | |
auto s = "hi"; // `s` has type `const char*`, `"hi"` has type `const char[3]` | |
// {...} disables implicit narrowing | |
int iii = 7.8; | |
int iii2 = {7.8}; | |
unsigned int x1 = -17; | |
unsigned int x2{-17}; | |
std::vector<int> v1{1, 2.3, 4, 5.6}; | |
double d{-1.23456}; | |
std::vector<int> v2{d}; // narrowing warning | |
char c{'a'}; | |
char c1{c + 1}; | |
char c3{static_cast<char>(c+1)}; | |
char c2 = c+1; | |
char c3(c+1); | |
// {...} can be used as initializer list | |
// - to pass multiple parameters to ordinary constructors | |
// - different types are allowed | |
// - as an std::initializer_list<> | |
// - must be homogeneous | |
// - only for {...} | |
// () initialization for ordinary constructors only | |
// {} initialization for *all* constructors | |
// - std::initializer_list<> constructors have higher priority | |
// - But the default constructor has highest priority | |
std::vector<std::string> v00 = "1"; // ERROR | |
std::vector<std::string> v01 = {}; // OK since C++14 | |
std::vector<std::string> v02 = {"1"}; | |
std::vector<std::string> v03 = {"1", "2"}; | |
std::vector<std::string> v04 = {{{"1"}, {"2"}}}; | |
std::vector<std::string> v05 = {{"1", "2", "3"}}; | |
std::vector<std::string> v06 = {{{"1", "2"}}}; // ERROR | |
std::vector<std::string> v07 = {{"1", "2"}}; // Fatal Runtime Error: taking the two arguments as iterators | |
// Constructors and type conversion operators define implicit conversions | |
// `explicit` disables implicit conversions | |
Data u; | |
Data v{}; | |
Data x{{"item", 6.7}, false}; | |
Data y{"item", 6.7, false}; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
GodBolt: https://godbolt.org/z/z6xYPf