Предполагается, что short - это 16-битное целое число с 2-байтовым выравниванием и что мы используем 32-битную машину с x86. Я понимаю, что размер этой структуры будет 6 байтов.
Не обязательно. Реализация может включать отступы после любого или всех членов по своему усмотрению. Реализации обычно принимают такие решения, основываясь на соображениях выравнивания, но они не привязаны ни к этому, ни к какой-либо конкретной формуле.
Требование выравнивания для вашей структуры должно быть по крайней мере таким же большим, как наибольшее требование выравнивания любого члена, но это не значит много, потому что реализация C (или C ++) делает свой собственный выбор в отношении требований выравнивания скалярных типов, и потому что она может свободно выбирать более высокие требования выравнивания для агрегированных типов и типов объединения, чем это необходимо для удовлетворения требования к согласованности их членов. Исторически сложилось так, что некоторые реализации делали это при различных обстоятельствах. Таким образом, даже если мы предположим, что ваша реализация добавляет заполнение только для целей выравнивания, ваша структура все равно может быть больше шести байтов.
Реализации обычно придерживаются установленного двоичного интерфейса приложения , который будет указать правила выравнивания данных и компоновки, но это средство для достижения цели (двоичная совместимость), а не требование языка.
* 1015 адрес памяти.
Если тип структуры имеет требование выравнивания как минимум два, то не будет начинаться с нечетного адреса, если вы каким-то образом не заставите его каким-либо образом обмана указателя. Если вы сделаете так принудительно смещение, то поведение доступа к структуре через смещенный указатель будет неопределенным. На практике среди наиболее вероятных вариантов поведения в целом следующие: (i) он просто работает, (ii) он работает, но доступ замедляется, и (iii) доступ вызывает сигнал времени выполнения.
Добавляет ли он отступ к структуре, чтобы вместо этого она «начиналась» с четной?
Заполнение - это характеристика c типа не экземпляров, а первый байт типа никогда не является байтом заполнения. Скорее, если вы позволите реализации выделить объект, она правильно выровняет выделение для типа. То же самое применимо и в C ++, если вы используете обычный оператор new
(не размещение new
), и если вы выделяете память вручную с помощью malloc()
, то начало выделенного пространства гарантированно будет правильно выровнено для любого типа. Это может означать, что перед экземпляром есть пробел, который не приписывается какому-либо объекту, но не является «заполнением» в общепринятом смысле этого слова.
Поскольку массивы расположены как непрерывная последовательность объекты без зазоров, а размер каждого объекта кратен его требованиям к выравниванию, из этого следует, что, пока первый элемент массива правильно выровнен для его типа, так будут и все последующие элементы.
Более того, имеет ли значение, четный ли начальный адрес, но он начинается на полпути через СЛОВО процессора (т.е. наименьший читаемый блок памяти) или в его начале?
Не должно ' t имеет значение для вас . Если это имеет значение для оборудования или самой реализации C (C ++), тогда реализация должна принять это во внимание должным образом.
Означают ли ответы на любой из моих вопросов, что размер структуры варьируется в зависимости от того, где в памяти она создана? Означает ли это, что некоторые элементы структурных массивов унифицированного типа будут иметь размер в байтах, отличный от других?
Нет и нет. Требования к размеру и выравниванию каждого типа являются фиксированными характеристиками типа. Они не меняются от экземпляра к экземпляру. Требуемая взаимосвязь между этими характеристиками (размер, кратный требуемому согласованию) помогает гарантировать, что ни одна из них не будет изменяться. То, что они не меняются, освобождает реализацию от отслеживания метаданных на уровне экземпляра, что было бы расточительным.
Это также означает, что арифметика указателей c и индексирование массивов (которые, по сути, одно и то же) работают для массивов тип конструкции. Вы можете использовать любой механизм для доступа к элементам массива, независимо от информации о типе элемента.
Я также спрашиваю, есть ли какие-либо отличия, указанные c от этого topi c между c и c ++ .
C ++ имеет более богатую систему типов, чем C, но конгруэнтные части имеют по существу те же правила.
возможно ли, что данные структура, подобная этой, начинается в адресе памяти на полпути через СЛОВО памяти (т.е. наименьший читаемый блок памяти) в массиве или не в массиве?
Ни C, ни C ++ не запрещают этого. Фактически, их вообще не интересует этот вопрос. Это зависит от реализации, и в некоторой степени для разных реализаций, ориентированных на одну и ту же операционную среду, возможно, сделать другой выбор.