Рассмотрим намеренно сломанную программу, модифицированную из Zed Shaw's C tutorial, который создает массив символов и листьев завершающего \0
объявление переменной:Разметка памяти и порядок
#include <stdio.h>
int main(int argc, char *argv[])
{
char name[] = "Zed";
char full_name[] = {
'Z', 'e', 'd',
' ', 'A', '.', ' ',
'S', 'h', 'a', 'w'
};
printf("name=\"%s\" and full_name=\"%s\"\n", name, full_name);
return 0;
}
Выход есть:
name="Zed" and full_name="Zed A. ShawZed"
И Комментарии Zed предполагают, что этот выход ожидается, т. Е. Память, похоже, сначала выкладывает full_name
, а затем name
, смежно. Это поведение указано в C? Компилятор всегда компонует память в обратном порядке? Если нет, то каков принцип, от которого он зависит?
Если изменить порядок, в котором мы объявляем переменные:
char full_name[] = {
'Z', 'e', 'd',
' ', 'A', '.', ' ',
'S', 'h', 'a', 'w'
};
char name[] = "Zed";
Тогда мы получим ожидаемые символы мусора в конце несогласованного массив символов:
name="Zed" and full_name="Zed A. Shaw4¦h4¦¦+"
Вы в сферах неопределенного поведения. Во всяком случае, почему вы пишете глупый код? –
Часть подхода Зеда заключается в том, чтобы учить вас, чтобы вы намеренно нарушили код, чтобы лучше понять внутренности. Если вы прочтете ссылку, это будет иметь смысл. – Jonah
Все, что вы узнали об этой конкретной реализации компилятора на этом уровне оптимизации. У вас есть интерес к продвижению ссылки? –