Есть пара отличий. Наиболее важно, если вы переполняете допустимый диапазон символа, назначая ему слишком большое или маленькое целое число, и символ подписывается, результирующее значение определяется реализацией, или даже некоторый сигнал (в C) может быть повышен, как для всех типов со знаком. , Сравните это с тем случаем, когда вы назначаете что-то слишком большое или маленькое для беззнакового символа: значение оборачивается, вы получите точно определенную семантику. Например, присвоив -1 неподписанному символу, вы получите UCHAR_MAX. Поэтому, когда у вас есть байт, например число от 0 до 2 ^ CHAR_BIT, вы должны использовать неподписанный символ для его хранения.
Знак также имеет значение при переходе к функциям vararg:
char c = getSomeCharacter(); // returns 0..255
printf("%d\n", c);
Предположим, что значение, назначенное c, будет слишком большим для представления char, и машина использует дополнение до двух. Многие реализации ведут себя в случае, когда вы присваиваете слишком большое значение для символа, в котором битовый шаблон не изменится. Если int сможет представлять все значения char (что и есть для большинства реализаций), то char передается в int перед передачей в printf. Таким образом, ценность того, что передается, будет отрицательной. Повышение до int сохранит этот знак. Таким образом, вы получите отрицательный результат. Однако если char без знака, то значение без знака, и повышение до int даст положительное значение int. Вы можете использовать unsigned char, тогда вы получите точно определенное поведение как для присваивания переменной, так и для передачи в printf, которая затем выведет что-то положительное.
Обратите внимание, что символы char, unsigned и char имеют ширину и ширину не менее 8 бит. Не требуется, чтобы символ был в точности 8 бит в ширину. Однако для большинства систем это правда, но для некоторых вы обнаружите, что они используют 32-битные символы. Байт в C и C ++ определен так, чтобы иметь размер char, поэтому байт в C также не всегда точно равен 8 битам.
Другое отличие состоит в том, что в C беззнаковый символ не должен иметь битов заполнения. То есть, если вы обнаружите, что CHAR_BIT равно 8, то значения без знака должны быть в диапазоне 0 .. 2 ^ CHAR_BIT-1. То же самое верно для символа, если он без знака. Что касается знакового символа, вы не можете предполагать что-либо о диапазоне значений, даже если вы знаете, как ваш компилятор реализует материал знака (дополнение к двум или другие параметры), в нем могут быть неиспользуемые биты заполнения. В C ++ нет битов заполнения для всех трех типов символов.