What are undefined, unspecified, and implementation-defined behavior?

In C++, the terms undefined behavior, unspecified behavior, and implementation-defined behavior refer to different scenarios that can occur during program execution where the outcome cannot be reliably predicted by the C++ standard.

Undefined Behavior

Undefined behavior refers to operations for which the standard provides no definition, meaning that the compiler can do anything it wants—including crashing the program, producing unexpected results, or simply ignoring the operation altogether.

Example: Dereferencing a null pointer.

int* p = nullptr; *p = 10; // Undefined behavior

Unspecified Behavior

Unspecified behavior means that the C++ standard allows for multiple valid implementations or outcomes, but does not require that the behavior must be the same every time. The results may vary across different executions.

Example: The order of evaluation of function arguments.

void func(int a, int b); func(getValue(), getValue()); // The order of `getValue` calls is unspecified

Implementation-Defined Behavior

Implementation-defined behavior refers to choices made by the compiler implementation itself that may affect program behavior, but the standard requires the implementation to document these choices.

Example: The size of the `int` type may vary between implementations.

std::cout << "Size of int: " << sizeof(int) << std::endl; // Implementation-defined

undefined behavior unspecified behavior implementation-defined behavior C++