Зачем программисту C использовать escape-последовательности (oct/hex) для значений ASCII, а не десятичные?
Дополнение: связано ли это с производительностью или переносимостью?
Пример:
char c = '\075';
Зачем программисту C использовать escape-последовательности (oct/hex) для значений ASCII, а не десятичные?
Дополнение: связано ли это с производительностью или переносимостью?
Пример:
char c = '\075';
Вы используете восьмеричное или шестнадцатеричное число, потому что нет способа указать десятичные коды внутри символьного литерала или строкового литерала. Восьмеричный код преобладал в коде PDP-11. В наши дни, вероятно, имеет смысл использовать шестнадцатеричный формат, хотя '\0'
более компактен, чем '\x0'
(поэтому используйте '\0'
, когда вы завершаете строку нулем и т. д.).
Кроме того, имейте в виду, что "\x0ABad choice"
не имеет того значения, которое вы могли бы ожидать, в то время как "\012007 wins"
, вероятно, имеет. (Разница в том, что шестнадцатеричный escape-код работает до тех пор, пока не встретит не шестнадцатеричную цифру, тогда как восьмеричный escape-код останавливается не более чем после 3 цифр. Чтобы получить ожидаемый результат, вам понадобится "\x0A" "Bad choice"
, используя «конкатенацию смежных строковых литералов».)
И это никак не связано с производительностью и очень мало связано с портативностью. Написание '\x41'
или '\101'
вместо 'A'
— это способ уменьшить переносимость и читабельность вашего кода. Вы должны рассмотреть возможность использования escape-последовательностей только в том случае, если нет лучшего способа представить символ.
'\012'
, также известный как control-L и обычно эквивалентный '\f'
(form-feed); остаток "007 wins"
. Так что да, восьмеричные escape-последовательности останавливаются не более чем после 3 восьмеричных цифр, но шестнадцатеричные escape-последовательности останавливаются на первой нешестнадцатеричной цифре.
- person Jonathan Leffler; 08.01.2015
Нет, это не имеет ничего общего с производительностью и портативностью. Это всего лишь один удобный способ определить символьные литералы и использовать их в строковых литералах специально для непечатаемых символов.
Это не имеет ничего общего с производительностью или портативностью. На самом деле никаких кодов вообще не нужно, вместо этого:
char c = 65;
Вы можете просто написать:
char c = 'A';
Но некоторые символы не так просто ввести, например. ASCII SOH, поэтому вы можете написать:
char c = 1; // SOH
Или любая другая форма, шестнадцатеричная, восьмеричная, в зависимости от ваших предпочтений.
Это не имеет ничего общего ни с производительностью, ни с портативностью. Просто набор символов ASCII (как и его производные вплоть до UTF) организован в байтах и битах. Например, 32 первых символа являются управляющими символами, 32 = 040 = 0x20, ASCII-код «A» — это 65 = 0101 = 0x41, а «a» — это 97 = 0141 = 0x61, ASCII-код «0» — это 48 = 060 = 0x30.
Не знаю, как вам, а мне '0x30' и 0x'41' легче запомнить и использовать в ручных операциях, чем 48 и 65.
Кстати, байт представляет ровно все значение от 0 до 255, то есть от 0 до 0xFF...
Я не знал, что это работает.
Но у меня тут же возникла довольно полезная идея.
Представьте, что у вас мало памяти, и вы должны использовать систему разрешений, такую как права доступа к папкам unix.
Допустим, есть 3 группы и для каждой группы 2 разных варианта, которые можно разрешить или запретить.
0 означает ни один из обоих вариантов,
1 означает, что разрешен первый вариант,
2 означает, что второй вариант разрешен и
3 означает, что оба разрешены.
Чтобы сохранить разрешения, вы можете сделать это так:
char* bar = "213"; // first group has allowed second option, second group has first option allowed and third has full acces.
Но у вас есть четырехбайтовое хранилище для этой информации.
Конечно, вы можете просто преобразовать это в десятичную запись. Но это менее читабельно.
Но теперь, когда я это знаю....
делает:
char bar = '\0213';
Это довольно читабельно, а также экономит память! Я люблю это :D
8
не является допустимой восьмеричной цифрой, не так ли? - person M Oehm   schedule 08.01.2015'\085'
, это была многосимвольная символьная константа с нулем, за которым следовали цифры 8 и 5, что приводило к всевозможным странностям. Многосимвольные символьные константы имеют интерпретацию, определяемую реализацией, и присвоение одной простойchar
(вместо, возможно, простойint
) приводит к путанице. GCC выдавал ошибки (потому что компилирую с-Werror
):x.c:2:10: error: multi-character character constant [-Werror=multichar]
иx.c:2:10: error: overflow in implicit constant conversion [-Werror=overflow]
- person Jonathan Leffler   schedule 08.01.2015