is-integer-like , is-signed-integer-like

From cppreference.com
Iterator library
Iterator concepts
is-integer-like
is-signed-integer-like
(C++20) (C++20)
Iterator primitives
Algorithm concepts and utilities
Indirect callable concepts
Common algorithm requirements
(C++20)
(C++20)
(C++20)
Utilities
(C++20)
Iterator adaptors
Range access
(C++11) (C++14)
(C++14) (C++14)
(C++11) (C++14)
(C++14) (C++14)
(C++17) (C++20)
(C++17)
(C++17)
template < class T >
constexpr bool /*is-integer-like*/ = /* see description */ ;
(1) (since C++20)
( exposition only* )
template < class T >
constexpr bool /*is-signed-integer-like*/ = /* see description */ ;
(2) (since C++20)
( exposition only* )
1) /*is-integer-like*/ < T > is true if and only if T is an integer-like type.
2) /*is-signed-integer-like*/ < T > is true if and only if T is a signed-integer-like type.

Integer-class type

A type T is an integer-class type if it is in a set of implementation-defined types that behave as integer types do, as defined below . An integer-class type is not necessarily a class type .

An integer-class type can represent 2 N consecutive integers, where N , a positive integer, is called the width of the integer-class type.

An integer-class type is either signed or unsigned:

  • A signed integer class type can represent all integers in [ -2 N-1 , 2 N-1 -1 ] , where N is greater than the width of every signed integral type.
  • An unsigned integer class type can represent all integers in [ 0 , 2 N -1 ] , where N is greater than the width of every unsigned integral type.

All integer-class types model regular and three_way_comparable < std:: strong_ordering > .

A value-initialized object of integer-class type has value ​ 0 ​ .

An expression E of integer-class type T is contextually convertible to bool as if by bool ( E ! = T ( 0 ) ) .

Integer-like type

A type other than (possibly cv-qualified) bool is integer-like if it models integral or if it is an integer-class type.

  • An integer-like type is signed-integer-like if it models signed_integral or if it is a signed-integer-class type.
  • An integer-like type is unsigned-integer-like if it models unsigned_integral or if it is an unsigned-integer-class type.

Required behaviors

Expressions of integer-class type are explicitly convertible to any integer-like type, and implicitly convertible to any integer-class type of equal or greater width and the same signedness. Expressions of integral type are both implicitly and explicitly convertible to any integer-class type. Conversions between integral and integer-class types and between two integer-class types do not exit via an exception. The result of such a conversion is the unique value of the destination type that is congruent to the source modulo 2 N , where N is the width of the destination type.

Let Int<T> denote the following type:

  • If T is an integer-class type, Int<T> is a unique hypothetical extended integer type of the same signedness with the same width as T .
  • If T is an integral type, let Int<T> is the same type as T .

Given the following types, values and operators:

Type Definition
IC an integer-class type
IL an integer-like type
Value Definition
a an object of type IC
b an object of type IL
c an lvalue of an integeral type
x an object of type Int<IC> that represent the same value as a
y an object of type Int<IL> that represent the same value as b
Operator Definition
@ = one of + = , - = , * = , / = , % = , & = , | = , ^ = , <<= and >>=
@ one of + , - , * , / , % , & , | , ^ , << , >> , && , || , == , ! = , < , > , <= , >= , <=> and ,

The following expressions must be well-formed and have their specified result and effects if the specified conditions are satisfied:

Expression Condition Result Effects
a ++ No condition a prvalue of type IC whose value is equal to that of a prior to the evaluation modifies the value of a by adding 1 to it
a -- modifies the value of a by subtracting 1 to it
++ a expression-equivalent to a + = 1
-- a expression-equivalent to a - = 1
& a expression-equivalent to std:: addressof ( a )
! a ! x is well-formed same as ! x
+ a + x is well-formed same as + x , but has type IC same as + x
- a - x is well-formed same as - x , but has type IC same as - x
~a ~x is well-formed same as ~x , but has type IC same as ~x
c @ = a c @ = x is well-formed an lvalue referring to c same as c @ = x
a @ = b x @ = y is well-formed an lvalue referring to a same as x @ = y , except that the value that would be stored into x is stored into a
a @ b x @ y is well-formed same as x @ y , but the result type is different:
  • If x @ y is of type Int<IC> , the result has type IC .
  • If x @ y is of type Int<IL> , the result has type IL .
  • If x @ y is of any other type T , the result has type T .
same as x @ y
b @ a y @ x is well-formed same as y @ x , but the result type is different:
  • If y @ x is of type Int<IC> , the result has type IC .
  • If y @ x is of type Int<IL> , the result has type IL .
  • If y @ x is of any other type T , the result has type T .
same as y @ x

Defect reports

The following behavior-changing defect reports were applied retroactively to previously published C++ standards.

DR Applied to Behavior as published Correct behavior
LWG 3366
( P2393R1 )
C++20 the conversion between an integer-class type and its corresponding
integer type was not guaranteed to produce a representable value
guaranteed
LWG 3376
( P2393R1 )
C++20 integer-class types could only be class types also allowed
non-class types
LWG 3467 C++20 bool was considered as an integer-like type excluded
LWG 3575
( P2393R1 )
C++20 integer-class types were not guaranteed to be three-way-comparable guaranteed

See also

specifies that a semiregular type can be incremented with pre- and post-increment operators
(concept)