Встроенные типы C++

  1. Тип bool предназначен для хранения логического значения (true, false). Занимает 1 байт.
  2. Тип char предназначен для хранения символов или целых чисел. Занимает минимум 1 байт.
    • signed char signed спецификатор говорит компилятору, что последний бит (обозначен цветом на картинке) должен использоваться для хранения знака. Если он 1, то число отрицательное, если 0, то число положительное.
    • unsigned char unsigned спецификатор говорит компилятору, что последний знаковый бит должен использоваться для представления данных.
  3. Тип wchar_t предназначен для хранения "широких" символов (UTF-16). Занимает 2 байта. Его использовать не рекомендуют из-за отсутствия переносимости и пр. Более широкий обзор недостатков wchar_t Вы можете почитать на сайте utf8everywhere. Основная мысль манифеста, размещенного на сайте: "... мы считаем, что добавление wchar_t в стандарт C++ было ошибкой...".
  4. Тип int предназначен для хранения целых чисел. Обычно занимает 4 байта, но спецификаторы могут изменять это значение: уменьшить до 2 байт или увеличить до 8 байт.
    • short int short спецификатор изменяет значение, поддерживаемое типом данных int, на минимальное -- 2 байта.
      • signed short int signed спецификатор говорит компилятору, что последний бит (обозначен цветом на картинке) должен использоваться для хранения знака. Если он 1, то число отрицательное, если 0, то число положительное.
      • unsigned short int unsigned спецификатор говорит компилятору, что последний знаковый бит должен использоваться для представления данных.
    • long int long спецификатор изменяет значение, поддерживаемое типом данных int, на не меньшее 4 байт (4 байта на 32-битной машине и 8 байт на 64-битной машине).
      • signed long int signed спецификатор говорит компилятору, что последний бит (обозначен цветом на картинке) должен использоваться для хранения знака. Если он 1, то число отрицательное, если 0, то число положительное.
      • unsigned long int unsigned спецификатор говорит компилятору, что последний знаковый бит должен использоваться для представления данных.
    • long long int long long спецификатор изменяет значение, поддерживаемое типом данных int, на максимальное -- 8 байт.
      • signed long long int signed спецификатор говорит компилятору, что последний бит (обозначен цветом на картинке) должен использоваться для хранения знака. Если он 1, то число отрицательное, если 0, то число положительное.
      • unsigned long long int unsigned спецификатор говорит компилятору, что последний знаковый бит должен использоваться для представления данных.
  5. Тип float предназначен для хранения вещественных чисел с одинарной точностью. Обычно занимает 4 байта.
  6. Тип double предназначен для хранения вещественных чисел с двойной точностью. Обычно занимает 8 байт.
    • long double

Размеры типов для 64-битной машины:

Вопросы с собеседований на эту тему:

  1. Что выведет в консоль следующая программа:
    #include <iostream> int main(){ std::cout << 7u - 13; }

  2. Сколько раз выведется на экран надпись boo:
    #include <iostream> int main(){ unsigned char h = 128; for (unsigned char i = 0; i < 2 * h; ++i){ std::cout << "boo" << std::endl; } }

  3. Что выведется на экран консоли и почему?
    #include <iostream> int main(){ unsigned char boo = (unsigned char)256; if(boo){ std::cout << "boo is true" << std::endl; }else{ std::cout << "boo is false" << std::endl; } }

  4. Есть ли в следующем коде ошибка? Если есть то, какая?:
    #include <iostream> int main(){ size_t size = 24; while ( --size >= 0 ){ //... } }

  5. Чему будет равно a, после выполнения следующего кода:
    #include <iostream> int main(){ int a = 130; char c = a; a = c; }

Ответы:

Ответ: 4294967290.
Объяснение: в выражении cout << 7u - 13 арифметический оператор имеет бОльший приоритет, чем <<. При вычитании int из unsigned int -13 будет приведено к unsigned int, что даст переполнение и int(-13) => (unsigned int)(2^32-13) = 4294967283. А затем будет произведено сложение 7 + 4294967283 = 4294967290.
Ответ: цикл будет выполняться бесконечно.
Объяснение: 2*h = 256, а 256 в unsigned char вызовет переполнение и условие прекращения цикла превратится в for (unsigned char i = 0; i < 0; ++i), что не выполнится никогда.
Ответ: "boo is false".
Объяснение: unsigned char boo будет равно 0, так как в этом типе могут храниться значения <= 255, а 256 вызовет переполнение. При приведении к bool в if, мы получим false.
Ответ: цикл будет выполняться бесконечно.
Объяснение: size_t -- это typedef для unsigned int, значит, всегда положительное число и при переходе через 0 превратится не в отрицательное число, а в максимальное для этого типа: 2^32-1. Следовательно, условие цикла будет верно всегда.
Ответ: a = -126.
Объяснение: char может хранить числа от -128 до 127. 130 при приведении к char вызовет переполнение (эх.. опять, кому уже надоело это слово?) и -128 + (130 mod 128) = -126