висячий указатель, причина изменения стоимости после free ()?

В следующем сегменте кода, после free(x) , почему y становится 0?

По моему пониманию, память в куче, на которую указывает x , и все еще указывается на y , не была выделена кому-то еще, так как она может измениться на 0?

И более того, я не думаю, что это free(x) которые изменили его на 0.

Любые комментарии?

 #include  int main(int argc, char *argv[]) { int *y = NULL; int *x = NULL; x = malloc(4); *x = 5; y = x; printf("[%d]\n", *y); //prints 5 free(x); printf("[%d]\n", *y); //why doesn't print 5?, prints 0 instead return 0; } 

    Это неопределенное поведение, объяснения – это просто спекуляция.

    Я могу предположить, что, возможно, вы используете отладочную версию библиотеки C и что отладочная версия free () делает нулевую область.

    То, что делается free зависит от реализации. Не освобождает память после освобождения.

    И то, что вы делаете, – это неопределенное поведение.

    Не указывает ли y на тот же адрес, что и x , после строки

    y = x;

    Если вы освободите x , вы также освободите память, указанную y .

    Если вам интересно, почему он печатает «0», это неопределенное поведение, но я уже видел это как практику, что некоторые программисты задают освобожденную область «0».

    Загрузите это видео под названием «Binky the pointer fun video» (это не шутка, на самом деле очень воспитательная), и вы получите лучшие указатели.

    Вызов free() поместит блок памяти, который был выделен malloc() обратно в структуры данных, которые среда выполнения C поддерживает для кучи (в этом случае что-то, что можно назвать «свободным списком»).

    Манипулирование структурами данных кучи может случайно изменить то, на что указывает y (поскольку программа больше не владеет памятью, у нее нет оснований полагать, что память не должна меняться).

    В не-отладочной версии программы среда выполнения обычно не будет делать ничего специально, чтобы сделать недействительной освобожденную память, но, как я уже упоминал, она все равно может внести изменения в результате собственной бухгалтерии (хотя, поскольку память не принадлежит для вызывающего абонента, время выполнения позволяет делать все, что ему нравится).

    В сборке отладки среда выполнения, вероятно, явно перезапишет память до значения, которое может быть недействительным, если программа использует его в надежде на то, что это вызовет проблему, которая легче идентифицирует проблему. Обычно значение, используемое для перезаписи освобожденного блока памяти, не равно нулю, так как нуль часто не обнаруживает ошибку (т. Е. Проверки указателя NULL заставят код «обрабатывать» недопустимый доступ к памяти). Например, менеджер кучи памяти MSVC перезапишет освобожденную память со значением 0xDD (см. Раздел « Когда и почему для инициализации памяти ОС необходимо установить 0xCD, 0xDD и т. Д. На malloc / free / new / delete?» ).