# Expressions

From cppreference.com
< cpp‎ | language

An expression is a sequence of operators and their operands, that specifies a computation.

Expression evaluation may produce a result (e.g., evaluation of 2+2 produces the result 4) and may generate side-effects (e.g. evaluation of std::printf ("%d",4) prints the character '4' on the standard output).

#### General

- value categories (lvalue, rvalue, glvalue, prvalue, xvalue) classify expressions by their values
- order of evaluation of arguments and subexpressions specify the order in which intermediate results are obtained

### Operators

Common operators
assignment | increment decrement | arithmetic | logical | comparison | member access | other
a = b a += b a -= b a *= b a /= b a %= b a &= b a |= b a ^= b a <<= b a >>= b | ++a --a a++ a-- | +a -a a + b a - b a * b a / b a % b ~a a & b a | b a ^ b a << b a >> b | !a a && b a || b | a == b a != b a < b a > b a <= b a >= b a <=> b | a[b] *a &a a->b a.b a->*b a.*b | a(...) a, b ? :
Special operators

`static_cast` converts one type to another related type
`dynamic_cast` converts within inheritance hierarchies
`const_cast` adds or removes cv qualifiers
`reinterpret_cast` converts type to unrelated type
C-style cast converts one type to another by a mix of `static_cast`, `const_cast`, and `reinterpret_cast`
`new` creates objects with dynamic storage duration
`delete` destructs objects previously created by the new expression and releases obtained memory area
`sizeof` queries the size of a type
`sizeof...` queries the size of a parameter pack (since C++11)
`typeid` queries the type information of a type
`noexcept` checks if an expression can throw an exception (since C++11)
`alignof` queries alignment requirements of a type (since C++11)

- operator precedence defines the order in which operators are bound to their arguments
- alternative representations are alternative spellings for some operators
- operator overloading makes it possible to specify the behavior of the operators with user-defined classes.

#### Conversions

- standard conversions implicit conversions from one type to another
- `const_cast` conversion
- `static_cast` conversion
- `dynamic_cast` conversion
- `reinterpret_cast` conversion
- explicit cast conversion using C-style cast notation and functional notation
- user-defined conversion makes it possible to specify conversion from user-defined classes

#### Memory allocation

- new expression allocates memory dynamically
- delete expression deallocates memory dynamically

#### Other

- constant expressions can be evaluated at compile time and used in compile-time context (template arguments, array sizes, etc)
- `sizeof`
- `alignof`
- `typeid`
- throw-expression

### Primary expressions

The operands of any operator may be other expressions or primary expressions (e.g. in 1+2*3, the operands of operator+ are the subexpression 2*3 and the primary expression 1).

Primary expressions are any of the following:

1) Literals (e.g. 2 or "Hello, world")
2) Suitably declared unqualified identifiers (e.g. n or cout)
3) Suitably declared qualified identifiers (e.g. std::string::npos)
4) Lambda-expressions (C++11)
5) Fold-expressions (C++17)
6) Requires-expressions (C++20)

Any expression in parentheses is also classified as a primary expression: this guarantees that the parentheses have higher precedence than any operator. Parentheses preserve value, type, and value category.

#### Literals

Literals are the tokens of a C++ program that represent constant values embedded in the source code.

- integer literals are decimal, octal, hexadecimal or binary numbers of integer type.
- character literals are individual characters of type

  - char or wchar_t
  - char16_t or char32_t (since C++11)
  - char8_t (since C++20)

- floating-point literals are values of type float, double, or long double
- string literals are sequences of characters of type

  - const char[] or const wchar_t[]
  - const char16_t[] or const char32_t[] (since C++11)
  - const char8_t[] (since C++20)

- boolean literals are values of type bool, that is true and false
- `nullptr` is the pointer literal which specifies a null pointer value (since C++11)
- user-defined literals are constant values of user-specified type (since C++11)

### Unevaluated expressions

The operands of the operators `typeid`, `sizeof` , `noexcept`, and `decltype` (since C++11) are expressions that are not evaluated (unless they are polymorphic glvalues and are the operands of `typeid`), since these operators only query the compile-time properties of their operands. Thus, std::size_t n = sizeof( std::cout << 42); does not perform console output.

The unevaluated operands are considered to be full expressions even though they are syntactically operands in a larger expression (for example, this means that sizeof(T()) requires an accessible `T::~T`) | (since C++14)

The requires-expressions are also unevaluated expressions. An invocation of an immediate function is always evaluated, even in an unevaluated operand. | (since C++20)

### Discarded-value expressions

A discarded-value expression is an expression that is used for its side-effects only. The value calculated from such expression is discarded. Such expressions include the full expression of any expression statement, the left-hand argument of the built-in comma operator, or the argument of a cast-expression that casts to the type void.

Array-to-pointer and function-to-pointer conversions are never applied to the value calculated by a discarded-value expression. The lvalue-to-rvalue conversion is applied if and only if the expression is a volatile-qualified glvalue and has one of the following forms (built-in meaning required, possibly parenthesized)

- id-expression
- array subscript expression
- class member access expression
- indirection
- pointer-to-member operation
- conditional expression where both the second and the third operands are one of these expressions,
- comma expression where the right operand is one of these expressions.

In addition, if the lvalue is of volatile-qualified class type, a volatile copy-constructor is required to initialize the resulting rvalue temporary.

If the expression is a non-void prvalue (after any lvalue-to-rvalue conversion that might have taken place), temporary materialization occurs. Compilers may issue warnings when an expression other than cast to `void` discards a value declared `[[nodiscard]]`. | (since C++17)

Retrieved from "https://en.cppreference.com/mwiki/index.php?title=cpp/language/expressions&oldid=109221"