C++17 programming language

File structure

Source files use the extension .cpp, header files use .h (or rarely .hpp).

Declarations belong in header files, definitions belong in source files. Identifiers can be declared more than once (which allows header files to be included multiple times without error), but can be defined at most once.

Source files are compiled individually, with no knowledge of the contents of other files. Header files allow identifiers to be used from other files, by allowing the required declarations to be included at the top of every file. Header files also prevent the issue of forward declarations in the same file.

Source files are individually compiled into object files, and then those object files are linked together into an executable.

Types

Fundamental integral types

All types are signed by default, unless prefixed with unsigned.

Type Width
char at least 8
short at least 16
int at least 16
long at least 32
long long at least 64

int is the optimal integer size on the target platform.

bool is an integer type that can only hold the values 0 and 1.

wchar_t is a distinct type that is large enough to represent any supported character code point. This is 16 bits on Windows (uses UTF-16) and 32 bits on Linux (uses UTF-32). The types char8_t, char16_t, and char32_t also exist on all platforms.

Fixed-width integral types

These must be included first with #include <cstdint>.

Signed Unsigned Width
int8_t uint8_t exactly 8
int16_t uint16_t exactly 16
int32_t uint32_t exactly 32
int64_t uint64_t exactly 64

size_t is the optimal type for indexing into an array.

Strings

These must be included first with #include <string>.

All strings extend std::basic_string<T>. std::wstring is a Unicode string, using wchar_t as the character type. std::string is an ASCII string, using char as the character type.

Constants

There are a few different meanings of constant in C++:

  • const marks a value as immutable, preventing it from being modified.
  • constexpr marks a value as being calculated at compile-time.
  • * const indicates a constant pointer. The data behind the pointer can be modified, but the pointer itself cannot.
  • fn() const marks a constant method, preventing class members from being modified.
const int v = 2*3;          // value is immutable.
constexpr int v = 2*3;      // value is calculated at compile time.
int fibonacci(const int n); // function will not modify its argument.
int List::size() const;     // method will not modify any members.

Functions

A function can be a member of a class. The class name is part of the signature.

char& String::operator[](int index);

Collections

Vector

A resizeable homogeneous array, defined as std::vector in the vector library.

vector<unsigned int> list = { 1, 2, 3 };
list.at(0);
list[0];
list.size();

Map

Hashmaps are provided as std::unordered_map in the unordered_map library.

unordered_map<string, string> registry = {};
registry.insert({"key", "value"});
string v = registry["key"];

References

int  x = 1;  // x is 1
int& r = x;  // r is a reference to x
r = 2;       // x is 2

Passing by reference

Values can be passed by reference by adding a & character as a suffix to the argument in the function signature:

#include <iostream>
#include <vector>
using namespace std;

int sum_list(vector<int>& list) {
    int sum = 0;
    for (int element : list) {
        sum += element;
    }
    return sum;
}

int main() {
    vector<int> list = { 1, 2, 3 };
    cout << sum_list(list) << "\n";
}

rvalue reference

An rvalue (or ‘temporary’) is a value that is about to be destroyed. An rvalue reference, identified by T&&, refers to an rvalue that can be modified. It allows a value to be passed to a function with move semantics, rather than the default behaviour of copying the value and then immediately deleting the original instance.

int&& a = 5;

Pointers

Creating a pointer

Pointers are created with the & address-of syntax.

int x = 2;
int* p = &x;
*p = 3;

Pointer arithmetic

A pointer can be advanced to point to the following item of a sequence with the ++ operator.

Null pointer

The null pointer is called nullptr, and represents the absence of a value. It is used as the terminator for null-terminated strings.

There is only one nullptr shared by all pointer types.

Allocation

Objects can be allocated onto the heap with new, and deallocated with delete.

int* values = new int[10];
delete values;

Classes

Class members are private by default.

class Stack {
    private:
        uint8_t p;
        uint8_t mem[256];

    public:
        Stack();
};

Stack::Stack() : p{0}, mem{} {

}