# C++ Programming/Programming Languages/C++/Code/Statements/Variables/Type/Data Types
#### Data types

| Type | Size in Bits | Comments | Alternate Names |
| Primitive Types ||||
| char | ≥ 8 | May or may not be signed, The choice is implementation dependent. The fundamental memory unit is the byte. A char is 8 bits or more, and at least big enough to contain UTF-8 or implementation's full character set, which ever is larger and any character encoding of 8 bits or less (e.g. ASCII). Logical and arithmetic operations outside the range 0 ←→ +127 may lack portability. All bits contribute to the value of the char, i.e. there are no "holes" or "padding" bits. a char will represent the same values as either signed char or unsigned char as defined by the implementation. | — |
| signed char | same as char | Characters stored like for type char. Can store integers in the range -128 to 127 portably. | — |
| unsigned char | same as char | Characters stored like for type char. Can store integers in the range 0 to 255 portably. | — |
| short | ≥ 16, ≥ size of char | Can store integers in the range -32767 ~ 32767 portably. Used to reduce memory usage (although the resulting executable may be larger and probably slower as compared to using int. | short int, signed short, signed short int |
| unsigned short | same as short | Can store integers in the range 0 ~ 65535 portably. Used to reduce memory usage (although the resulting executable may be larger and probably slower as compared to using int. | unsigned short int |
| int | ≥ 16, ≥ size of short | Represents the "normal" size of data the processor deals with (the word-size); this is the integral data-type used normally. Can store integers in the range -32767 ~ 32767 portably. | signed, signed int |
| unsigned int | same as int | Can store integers in the range 0 ~ 65535 portably. | unsigned |
| long | ≥ 32, ≥ size of int | Can store integers in the range -2147483647 ~ 2147483647 portably. | long int, signed long, signed long int |
| unsigned long | same as long | Can store integers in the range 0 ~ 4294967295 portably. | unsigned long int |
| bool | ≥ size of char, ≤ size of long | Can store the constants true and false. | — |
| wchar_t | ≥ size of char, ≤ size of long | Signedness is implementation-defined. Can store "wide" (multi-byte) characters, which include those stored in a char and probably many more, depending on the implementation. Integer operations are better not performed with wchar_ts. Use int or unsigned int instead. | — |
| float | ≥ size of char | Used to reduce memory usage when the values used do not vary widely. The floating-point format used is implementation defined and need not be the IEEE single-precision format. unsigned cannot be specified. | — |
| double | ≥ size of float | Represents the "normal" size of data the processor deals with; this is the floating-point data-type used normally. The floating-point format used is implementation defined and need not be the IEEE double-precision format. unsigned cannot be specified. | — |
| long double | ≥ size of double | unsigned cannot be specified. | — |
| User Defined Types ||||
| struct or class | ≥ sum of size of each member | Default access modifier for structs for members and base classes is public. For classes the default is private. The convention is to use struct only for Plain Old Data types. Said to be a compound type. | — |
| union | ≥ size of the largest member | Default access modifier for members and base classes is public. Said to be a compound type. | — |
| enum | ≥ size of char | Enumerations are a distinct type from ints. ints are not implicitly converted to enums, unlike in C. Also ++/-- cannot be applied to enums unless overloaded. | — |
| typedef | same as the type being given a name | Syntax similar to a storage class like static, register or extern. | — |
| template | ≥ size of char | — | — |
| Derived Types ||||
| type& (reference) | ≥ size of char | References (unless optimized out) are usually internally implemented using pointers and hence they do occupy extra space separate from the locations they refer to. | — |
| type* (pointer) | ≥ size of char | 0 always represents the null pointer (an address where no data can be placed), irrespective of what bit sequence represents the value of a null pointer. Pointers to different types may have different representations, which means they could also be of different sizes. So they are not convertible to one another. Even in an implementation which guarantees all data pointers to be of the same size, function pointers and data pointers are in general incompatible with each other. For functions taking variable number of arguments, the arguments passed must be of appropriate type, so even 0 must be cast to the appropriate type in such function-calls. | — |
| type [integer] (array) | ≥ integer × size of type | The brackets () follow the identifier name in a declaration. In a declaration which also initializes the array (including a function parameter declaration), the size of the array (the integer) can be omitted. type is not the same as type*. Only under some circumstances one can be converted to the other. | — |
| type (comma-delimited list of types/declarations) (function) | — | The parentheses () follow the identifier name in a declaration, e.g. a 2-arg function pointer: int (* fptr) (int arg1, int arg2). Functions declared without any storage class are extern. | — |
| type aggregate_type::* (member pointer) | ≥ size of char | 0 always represents the null pointer (a value which does not point to any member of the aggregate type), irrespective of what bit sequence represents the value of a null pointer. Pointers to different types may have different representations, which means they could also be of different sizes. So they are not convertible to one another. | — |
$^{[1]}$ -128 can be stored in two's-complement machines (i.e. almost all machines in existence). In other memory models (e.g. 1's complement) a smaller range is possible, e.g. -127 ←→ +127. :
| $^{[2]}$ -32768 can be stored in two's-complement machines (i.e. most machines in existence). |||
| $^{[3]}$ -2147483648 can be stored in two's-complement machines (i.e. most machines in existence). |||
| $^{[4]}$ The precedences in a declaration are: |, (left associative) | — Highest |
| | &, *, ::* (right associative) | — Lowest |