Может ли кто-нибудь объяснить этот маленький фрагмент кода для меня?
Дано:
int a[3] = {2,3,4};
Почему следующее оценивается как истинное?
static_cast<void *>(a) == static_cast<void *>(&a); // Why is this true?
Это говорит о том, что address of a
такой же как a
? Если так, то почему это так?
Это потому, что адрес переменной a
совпадает с адресом первого элемента массива a
, Вы также можете думать о a
является &a[0]
что понятнее, когда мы говорим «адрес первого элемента массива»).
Другой пример,
struct X
{
int i;
};
X x;
Вот и адрес переменной x
соглашается с адресом x.i
(который является первым элементом совокупности), так что это напечатало бы 1
:
std::cout << (&x == &(x.i)) << std::endl; //1
Так что в вашем случае, &a
как &x
, а также a
(или же &a[0]
) как &(x.i)
,
Обратите внимание, что в C ++ a
а также x
оба называются агрегатными (см. мой ответ здесь: Что такое агрегат?)
Почти во всех контекстах имя массива превращается в указатель на первый элемент массива. Так в static_cast<void*>(a)
, a
разлагается в &a[0]
; это тип «указатель на int». Выражение вычисляется по адресу первого элемента массива. В static_cast<void*>(&a)
, тем не мение, &a
адрес самого массива; его тип — «указатель на массив из 3 int». Вот почему здесь нужны приведения: два выражения без приведения имели бы разные типы и не могли бы сравниваться. Оба могут быть преобразованы в void*
и сравнил. Итак, этот код иллюстрирует то, что адрес первого элемента массива совпадает с адресом массива, то есть, там нет набивки на передней панели.
Имя массива обычно вычисляется по адресу первого элемента массива, поэтому массив и &массив имеет точно такое же значение.
Однако они бывают разных типов. Для следующего массива:
int a[8];
a + 1 — адрес массива a + sizeof (int)
но &+ 1 будет адресом массива a + 8 * sizeof (int).