Может ли быть так, что sizeof (T*)!= sizeof (const T*)?
я спорю с моим боссом об этом. Они говорят: "Да они могут быть разными."
возможно sizeof(T*) != sizeof(const T*)
для типа T
?
4 ответа:
нет, они не могут быть разными. Для достаточно разных
T1
иT2
,sizeof(T1 *)
можноsizeof(T2 *)
, а еслиT2
это простоconst T1
, тогда:3.9.2 типы соединений [основные.соединение]
3 [...] Указатели на cv-квалифицированные и cv-неквалифицированные версии (3.9.3) совместимых с макетом типов должны иметь одинаковые требования к представлению значений и выравниванию (3.11). [...]
и любой типа
T
макет-совместим с самим собой:3.9 типы [основная.типы]
11 Если два типа
T1
иT2
имеют тот же тип, тоT1
иT2
are макет-совместимый типы. [...]
представление значения связано с представлением объекта, вы не можете иметь одно и то же представление значения без того же представления объекта. Последний означает, что требуется одинаковое количество битов.
3.9 типы [основная.типы]
4 The представление объектов объект типа
T
последовательность Nunsigned char
объекты, занятые объектом типаT
, где N равнаsizeof(T)
. Элемент представление значения объекта-это набор битов, которые содержат значение типаT
. Для тривиально копируемым типы, представление значения-это набор битов в представлении объекта, который определяет стоимостью, который является одним дискретным элементом реализации определенного набора значений.4444) цель состоит в том, что модель памяти C++ совместима с моделью языка программирования ISO/IEC 9899 C.
суть требования, причина, по которой он не просто говорит, что два типа имеют одно и то же представление объекта, такова это
T *
иconst T *
не только имеют одинаковое количество битов, но и то, что это те же биты вT *
иconst T *
, которые составляют стоимость. Это должно гарантировать не только этоsizeof(T *) == sizeof(const T *)
, а это означает, что вы можете использоватьmemcpy
чтобы скопировать aT *
значение указателя наconst T *
значение указателя или наоборот и получить значимый результат, тот же результат, который вы получите сconst_cast
.требования к выравниванию также предоставляют некоторые дополнительные гарантии, но они сложны для правильного объяснения и не имеют прямого отношения к этому вопросу, и в стандарте есть проблемы, которые подрывают некоторые из предполагаемых гарантий, поэтому я думаю, что здесь лучше всего игнорировать.
микрочип выпустил такой компилятор C, где
sizeof(T*)
было 2, ноsizeof(const T*)
было 3 года.компилятор C не был совместим со стандартами несколькими способами, поэтому это ничего не говорит об этом (я подозреваю, что это не так, и другие ответы согласны).
Хм, это очень эзотерично, но я думаю, что теоретически есть может быть архитектурой, которая имеет, скажем, 256 байт ОЗУ в адресе 0 и, скажем, несколько килобайт ПЗУ в более высоких адресах. А там может быть компилятором, который будет создавать 8-битный указатель для
int *i
потому что 8 бит достаточно для хранения адреса любого объекта в сильно ограниченной области ОЗУ, и любой изменяемый объект, конечно, неявно известен в области ОЗУ. Указатели типаconst int *i
потребуется 16 бит, так что они могли указывать на любое место в адресном пространстве. 8-битный указательint *i
может быть приведено к 16-битному указателюconst int *i
(но не наоборот), поэтому жидкотекучести требование стандарта C может быть удовлетворен.но если есть такая архитектура в existense, я бы хотел ее увидеть (но не писать код для нее):)
Что касается стандартного C++, они не могут отличаться. C и c++ похожи в этом отношении.
но есть много архитектур там с компиляторами, написанными для них, которые не следуют этому правилу. Действительно, тогда мы действительно не говорим о стандартном C++, и некоторые люди будут утверждать, что язык не является C++, но мое чтение вашего вопроса (до добавления тега адвоката языка) больше касается возможности.
в этом случае, это вероятный. Вы вполне можете обнаружить, что указатель на ROM (следовательно, const) имеет другой размер, чем указатель на RAM (const или non const.)
Если вы точно знаете, что ваш код будет работать только на компиляторе жалоб стандартов, то ваше предположение верно. Если нет, то я бы тщательно подумал о том, чтобы полагаться на то, что их размеры одинаковы.