Приведение строки C к беззнаковому указателю - PullRequest
0 голосов
/ 14 ноября 2011

Я компилирую код низкого уровня, используя много байтов. В некоторых случаях мне удобно определить, используя старые кавычки C в двойных кавычках.

Но при компиляции с помощью gcc или g ++ (не знаю поведения с другими компиляторами) меня беспокоит знак заостренной строки.

В основном, когда я пишу это

const unsigned char & refok = *"ABCDEFGHI";

РЕДАКТИРОВАТЬ : хорошо, приведенный выше код на самом деле не работает, так как теоретически он будет содержать ссылку на копию первого символа строки. Это на самом деле разрешает доступ ко всей строке с некоторыми компиляторами из-за оптимизации, но может сломаться в любое время.

или это

const unsigned char oktoo[10] =
    {'A','B','C','D','E','F','G','H','I',0};

компилятор ничего не говорит.

Но это однозначно отвергает:

const unsigned char * bad = "ABCDEFGHI";

с сообщением

error: invalid conversion from 
   ‘const char*’ to ‘const unsigned char*’
   [-fpermissive]

Это даже не предупреждение, это ошибка .

Мне интересно, почему этот вопрос должен вызывать больше проблем, чем при использовании ссылки или преобразовании отдельных символов из подписанных в неподписанные? Или я что-то упустил?

Ответы [ 2 ]

8 голосов
/ 14 ноября 2011

Я думаю, что вам не хватает много вещей!

Первая строка, вероятно, делает что-то совершенно не то, что вы думаете.(Это включает преобразование и увеличение продолжительности жизни временного.)

Вторая строка инициализирует каждый неподписанный символ из соответствующего символа в инициализаторе фигурных скобок.

В третьей строкекомпилятор верен: строковый литерал имеет тип const char *, и вы не можете преобразовать T* в U* в целом.

Обратите внимание, что стандарт явно требует, чтобы char, unsigned char иsigned char be различных типов.Причиной здесь является то, что char должен быть собственным байтовым типом платформы, в то время как два других являются целыми типами без знака и со знаком.Типы без знака / со знаком предназначены для алгебраических операций, а открытый тип - для взаимодействия с системой (например, аргументы командной строки и файловый ввод / вывод).

4 голосов
/ 14 ноября 2011

Неявные преобразования между числовыми типами разрешены; это то, что делают первые два. Неявные преобразования между различными типами указателей недопустимы (кроме преобразования указателя производного класса в указатель базового класса).

Обратите внимание, что первое не дает ссылку на первый символ массива. Он создает временную копию этого символа, преобразованную в тип unsigned char, и привязывает ссылку к нему, продлевая время жизни временного элемента до срока действия ссылки.

Секунда преобразует каждый char в списке инициализатора в unsigned char элемент массива.

Третья попытка конвертировать const char * в const unsigned char *; поскольку char и unsigned char являются разными типами, неявное преобразование указателя не допускается.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...