Вопрос

Мне всегда было интересно, почему стандартная библиотека C++ создала экземпляр Basic_[io]stream и всех его вариантов, используя метод char введите вместо unsigned char тип. char означает (в зависимости от того, подписано оно или нет), что у вас может быть переполнение и опустошение для таких операций, как get(), что приведет к значению задействованных переменных, определенному реализацией.Другой пример: вы хотите вывести неформатированный байт в поток ostream, используя его put функция.

Есть идеи?


Примечание:Я все еще не совсем убежден.Так что, если вы знаете окончательный ответ, вы все равно можете опубликовать его.

Это было полезно?

Решение

Возможно, я неправильно понял вопрос, но преобразование из unsigned char в char не является неопределенным, оно зависит от реализации (4.7-3 в стандарте C ++).

Тип однобайтового символа в C ++ - "char", а не "unsigned char". Это дает реализациям немного больше свободы для достижения наилучших результатов на платформе (например, орган по стандартизации мог полагать, что существуют процессоры, в которых арифметика байтов со знаком быстрее, чем арифметика байтов без знака, хотя это предположение с моей стороны). Также для совместимости с C. Результатом удаления такого рода экзистенциальной неопределенности из C ++ является C #; -)

Учитывая, что символ " char " Тип существует, я думаю, что обычные потоки имеют смысл использовать его, даже если его подпись не определена. Поэтому, возможно, на ваш вопрос ответили: «Почему C ++ просто не определяет char как неподписанный?»

Другие советы

Я всегда понимал это так:цель iostream предназначен для чтения и/или записи потока символов, которые, если подумать, представляют собой абстрактные сущности, которые представляются компьютером только с использованием кодировки символов.Стандарт C++ прилагает большие усилия, чтобы избежать строгого определения кодировки символов, говоря только, что «Объекты, объявленные как символы (char) должен быть достаточно большим, чтобы хранить любой элемент базового набора символов реализации», поскольку не требуется принудительно заставлять «базовый набор символов реализации» определять язык C++;стандарт может оставить решение который для реализации используется кодировка символов (компилятор вместе с реализацией STL), и просто обратите внимание, что char объекты представляют собой отдельные символы в некоторой кодировке.

Автор реализации может выбрать однооктетную кодировку, например ИСО-8859-1 или даже двухоктетную кодировку, например УКС-2.Это не имеет значения.Пока char объект «достаточно велик, чтобы хранить любой элемент базового набора символов реализации» (обратите внимание, что это явно запрещает кодировки переменной длины), то реализация может даже выбрать кодировку, представляющую базовую латиницу, несовместимую с любой распространенной кодировкой!

Сбивает с толку то, что char, signed char, и unsigned char типы имеют в своих именах «char», но важно помнить, что char не принадлежит к тому же семейству фундаментальных типов, что и signed char и unsigned char. signed char принадлежит к семейству целочисленных типов со знаком:

Есть четыре целочисленные типы со знаком:«подписанный символ», «короткое целое число», «целое число» и «длинное целое число».

и unsigned char относится к семейству беззнаковых целочисленных типов:

Для каждого целочисленного типа со знаком существует соответствующий (но другой) беззнаковый целочисленный тип:«беззнаковый символ», «беззнаковое короткое целое число», «беззнаковое целое число» и «беззнаковое длинное целое число», ...

Единственное сходство между char, signed char, и unsigned char типов заключается в том, что «[они] занимают одинаковый объем памяти и имеют одинаковые требования к выравниванию».Таким образом, вы можете reinterpret_cast от char * к unsigned char * для определения числового значения символа в наборе символов выполнения.

Чтобы ответить на ваш вопрос, причина, по которой STL использует char типом по умолчанию является то, что стандартные потоки предназначены для чтения и/или записи потоков символов, представленных char объекты, а не целые числа (signed char и unsigned char).Использование char по сравнению с числовым значением - это способ разделения задач.

char - для символов, unsigned char - для необработанных байтов данных, а подписанные символы - для хорошо подписанных данных.

Стандарт не указывает, будет ли подписанный или неподписанный символ использоваться для реализации char - он зависит от компилятора. Это только указывает, что " char " будет "достаточно" для хранения символов в вашей системе - так, как это было в те дни, то есть без ЮНИКОДА.

Использование " char " для персонажей это стандартный путь. Использование unsigned char - это хак, хотя оно будет соответствовать реализации char компилятором на большинстве платформ.

Я думаю, этот комментарий хорошо это объясняет. Цитировать:

  

char со знаком и без знака являются арифметическими, целочисленными типами, такими как int и unsigned int. С другой стороны, char явно предназначен для "I / O" тип, представляющий некоторую непрозрачную системную базовую единицу данных на вашей платформе. Я бы использовал их в этом духе.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top