Розмір символу ('a') в C / C ++


298

Який розмір символів у С та С ++? Наскільки я знаю, розмір char становить 1 байт і для C, і для C ++.

В:

#include <stdio.h>
int main()
{
    printf("Size of char : %d\n", sizeof(char));
    return 0;
}

В C ++:

#include <iostream>
int main()
{
    std::cout << "Size of char : " << sizeof(char) << "\n";
    return 0;
}

Несподіванок немає, і те і інше дає результат: Size of char : 1

Тепер ми знаємо , що персонажі представлені в вигляді 'a', 'b', 'c', '|', ... Так що я просто змінив вищевказані коди до цих:

В:

#include <stdio.h>
int main()
{
    char a = 'a';
    printf("Size of char : %d\n", sizeof(a));
    printf("Size of char : %d\n", sizeof('a'));
    return 0;
}

Вихід:

Size of char : 1
Size of char : 4

В C ++:

#include <iostream>
int main()
{
    char a = 'a';
    std::cout << "Size of char : " << sizeof(a) << "\n";
    std::cout << "Size of char : " << sizeof('a') << "\n";
    return 0;
}

Вихід:

Size of char : 1
Size of char : 1

Чому sizeof('a')повертає різні значення в C і C ++?


8
"%|"Формат вимагає intаргументу (або що - то , що сприяє int). sizeofдає результат типу size_t. Або перетворите на intвикористання ролі, або, якщо ваша реалізація підтримує його, використовуйте "%zu".
— Кіт Томпсон

Відповіді:


348

У C тип константи символу типу, як 'a'і насправді int, має розмір 4 (або якесь інше значення, що залежить від реалізації). У C ++ тип є char, розмір 1. Це одна з багатьох невеликих відмінностей між двома мовами.


12
У стандарті C ++ це розділ 2.13.2 / 1, в C 6.4.4.4, принаймні в документі, який я отримав.

14
+1 (За винятком того, що, хоча "розмір 4", очевидно, стосується платформи nthrgeek, це не обов'язково стосується всіх платформ.)
— sbi

28
@nthrgeek: Я лінуюся цитувати обидва стандарти, але стандарт C ++ має додаток, присвячений несумісності з C. У додатку C.1.1 в ньому йдеться про те, що "Тип літерального символу змінено з intна char, що пояснює поведінку. :)
— jalf

3
@nthrgeek: §6.4.4.4, параграф 10: "Константа цілочистого символу має тип int. Значення цілої константи символів, що містить єдиний символ, що перетворюється на однобайтовий символ виконання, є числовим значенням представлення відображеного символ трактується як ціле число. "
— Стівен Канон

7
@nthrgeek: Вам не слід просити стандартної довідки, якщо у вас немає аргументів щодо конкретного питання і ви хочете зрозуміти, чому інша людина має іншу думку. Якщо всі згодні, просто прийміть це. Ви (як розробник) маєте бути досить розумними, щоб швидко самостійно знайти таку загальну відповідь.
— Мартін Йорк

26

Як заявив Павло, це тому 'a', що це intв C, а charв C ++.

Я висвітлюю конкретну різницю між C і C ++ у чомусь, про що я писав кілька років тому, за посиланням: http://david.tribble.com/text/cdiffs.htm


4
Цікаво, але ви працюєте над оновленням цього (дуже детального) документа, щоб включити нові зміни в C ++ 11 та C11?
— Адам Розенфілд

Не зараз. Мій інтерес до C та C ++ значно зменшився за останні п’ять років.
— David R Tribble

3
Ух, я використав вашу роботу, щоб написати це, і ось ви на ТАК. Такий маленький світ!

17

У C тип буквених символів - це int та char у C ++. Це в C ++, необхідному для підтримки перевантаження функцій . Дивіться цей приклад:

void foo(char c)
{
    puts("char");
}
void foo(int i)
{
    puts("int");
}
int main()
{
    foo('i');
    return 0;
}

Вихід:

char

5

У мові С символи буквально не є charтипом. C розглядає буквений символ як ціле число. Отже, різниці між sizeof('a')і sizeof(1).

Отже, розмір символу буквалів дорівнює величині цілого числа в С.

У мові C ++ символом буквеним є тип char. Cppreference Сея:

1) вузька літера або звичайний буквений символ, наприклад , 'a'або , '\n'або '\13'. Такий буквальний має типchar і значення, що дорівнює представленню c-char у наборі символів виконання. Якщо c-char не може бути представлений як один байт у наборі символів виконання, літерал має тип int та значення, визначене реалізацією.

Так, у символі С ++ літерал - це тип char. Отже, розмір буквеного символу в C ++ становить один байт.

Ало, у своїх програмах ви використовували неправильний специфікатор формату для sizeofоператора.

C11 §7.21.6.1 (P9):

Якщо специфікація конверсії недійсна, поведінку не визначено.275) Якщо будь-який аргумент не є правильним типом для відповідної специфікації перетворення, поведінка не визначена.

Отже, ви повинні використовувати %zuспецифікатор формату замість %d, інакше це не визначена поведінка в C.


%zuне підтримується на багатьох платформах, але краща портативність, використання (int)sizeof(char)та форматування%d
— chqrlie

Значення буквених символів не обов'язково є відповідним кодом ASCII. Це залежить від джерел і наборів символів виконання та від того, charтип чи типово підписаний чи непідписаний.
— chqrlie
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.