Абсолютно да, если char
знаковый тип. C позволяет char быть подписанным или беззнаковым , а в G CC вы можете переключаться между ними с помощью -funsigned-char
и -fsigned-char
. Когда char подписан, это то же самое, что и
char c = -65;
printf("%c", c);
При переходе в printf переменная char
будет иметь расширенный знак до int
, поэтому printf также увидит - 65, как если бы оно было передано с константы. printf
просто не имеет возможности различать printf("%c", c);
и printf("%c", -65);
из-за продвижения по умолчанию в переменных c функциях.
Результат печати зависит от кодировки символов . Например, в кодировках ISO-8859-1 или Windows -1252 вы увидите ¿
, потому что (unsigned char)-65 == 0xBF
. В UTF-8 (который является кодировкой переменной длины) 0xBF не допускается в качестве символа в начальной позиции. Вот почему вы видите � это символ замены для недопустимых байтов
Скажите, пожалуйста, почему кодовая точка от 0 до 255 не отображается в символы от 0 до 255 в символах без знака. Я имею в виду, что они неотрицательны, поэтому не следует ли мне просто просматривать набор символов UTF-8 для их соответствующих значений?
Сопоставление выполняется не по относительной позиции в диапазоне, как вы думали , т.е. кодовая точка 0 отображается на CHAR_MIN
, кодовая точка 40 сопоставляется с CHAR_MIN + 40
, кодовая точка 255 отображается на CHAR_MAX
... В системах с двумя дополнениями это обычно простое сопоставление, основанное на значении битовой комбинации, когда рассматривается как неподписанный. Это потому, что значения обычно обрезаются из более широкого типа. В C символьный литерал, например 'a'
, имеет тип int. Предположим, что 'a'
отображается в кодовую точку 130 в некотором теоретическом наборе символов, тогда следующие строки эквивалентны
char c = 'a';
char c = 130;
В любом случае c
будет присвоено значение 'a'
после преобразования в char, т.е. (char)'a'
, что может быть отрицательным значением.
Таким образом, кодовые точки от 0 до 255 отображаются в символы от 0 до 255 в беззнаковых символах. Это означает, что кодовая точка 0x1F будет сохранена в виде символа (со знаком или без знака) со значением 0x1F. Кодовая точка 0xBF будет сопоставлена с 0xBF, если char беззнаковый, и -65, если char подписан
Я предполагаю 8-битный char для всего вышеперечисленного. Также обратите внимание, что UTF-8 - это кодировка для набора символов Unicode, это не кодировка сама по себе, поэтому вы не можете искать кодовые точки UTF-8