Странности в массивах C char - PullRequest
4 голосов
/ 22 мая 2009

Я наткнулся на этот странный результат, когда возился с массивами C:

char s[100] = "hello";
if(s == &s[0]) printf("true. ");
if(s == &s) printf("true.");
// output: true. true.

Я знаю, что s содержит ячейку памяти первого элемента, но есть ли способ найти адрес s (адрес указателя, который указывает на первый элемент)? Почему &s равно s? Не то чтобы это было полезно, но я хотел бы знать, что происходит под капотом.

Я не уверен, что разные компиляторы реализуют это по-разному, но я использую gcc.

Ответы [ 6 ]

10 голосов
/ 22 мая 2009

Если бы я сказал вам положить палец в место, где расположен массив символов s, а затем в место, где находится первый символ в массиве, разве они не будут одинаковыми?

9 голосов
/ 22 мая 2009

Это потому, что s не указатель, а массив. Массивы автоматически приводятся к указателям при необходимости (как в strcpy и т. Д.), Но не существует такой вещи, как «адрес указателя, который указывает на первый элемент». s - это всего лишь 100 байт в стеке; компилятор передает адрес этих 100 байтов вызовам функций всякий раз, когда необходим указатель.

4 голосов
/ 22 мая 2009

Массив s не содержит адрес памяти (т.е. указатель), он фактически содержит все символы.

C будет свободно преобразовывать массив в указатель на массив.

Указатель на массив такой же, как указатель на его первый элемент.

3 голосов
/ 22 мая 2009

& s [0] означает адрес первого элемента массива s. Тип & s [0] является char *.

& s означает адрес массива s. Тип & s - это char (*) [100].

& s [0] + 1 - адрес следующего 1 байта. Но & s + 1 - это адрес следующих 1 * 100 = 100 байт.

1 голос
/ 22 мая 2009

С другой стороны, вы также можете делать такие вещи:

char (*t)[100] = s;
if(t == &t[0]) printf("true 3. ");
if(t == &t) printf("true 4.");

В этом случае t действительно является указателем на массив символов, который имеет свое собственное хранилище и адрес. Случай 3 является истинным, а случай 4 - ложным .

0 голосов
/ 22 мая 2009
Value of &s, s and &s[0] are same, but their types are not same.
type of &s is char (*)[100], but type of s and &s[0] is char*.
&s is a pointer to the entire array but s and &s[0] points to
the first element of the array.
sizeof(&s) and sizeof(s) is 100, but sizeof(&s[0]) is 4.
Similarly if s = 1000, then &s+1 returns 1100 but s+1 and &s[0]+1 returns 1001.
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...