Почему значение 'x' печатается в main, если оно могло быть освобождено при выходе из abc ()? - PullRequest
0 голосов
/ 10 июня 2019

В упомянутом коде после назначения указателя на x в функции abc () он печатает значение x в abc (), после выхода из abc () указатель больше не должен указывать на x как ' x 'мог быть освобожден, и это должно привести к появлению висящего указателя, но это не так, он выводит значение' x 'также в main. Как?

#include <stdio.h>
void abc();
int* ptr = NULL;
void abc()
{ 
    int x = 10; 
    ptr = &x; 
    printf("in abc ptr: %d",*ptr);
    printf("\n");
} 
int main()
{
    abc();
    printf("in main ptr: %d",*ptr);
    return 0;
}

Ответы [ 4 ]

3 голосов
/ 10 июня 2019

То, что вам не разрешено что-либо делать, не означает, что это не сработает. С не гарантирует, что все, что вы делаете, является действительным. Указатель не указывает на допустимую переменную, но он указывает на память, которая может иметь правильный шаблон, равный int 10.

Вызов других функций, особенно той, которая использует локальные переменные, между вызовом abc и строкой printf может привести к перезаписи этого значения.

Как и сейчас, этот код вызывает неопределенное поведение .

2 голосов
/ 10 июня 2019

C такого рода проверок не выполняет, вы почти полностью отвечаете за управление памятью вашей программы.Тот факт, что значение в этом адресе памяти остается неизменным, несмотря на то, что стековый фрейм abc () больше не существует, является просто результатом «удачи».Чтобы быть более точным, этот эффект происходит, потому что C не имеет сборщика мусора.

1 голос
/ 10 июня 2019

То, что напечатано, является объектом по адресу, где x существовал .

Если ничто не использует эту память, значение, как правило, не изменится.Это является неопределенным поведением, но по большей части, когда не требуется ничего делать, компилятор C ничего не делает, и в этом случае это включает в себя не явное изменение памяти, ранее использовавшейся для x только потому, что x больше не находится в области видимости.

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

0 голосов
/ 10 июня 2019

По вдохновению комментария @JonathanLeffler попробуйте изменить функцию main на

int main()
{
    abc();
    printf("in main: ");
    printf("ptr: %d", *ptr);
    return 0;
}

и посмотрите, что произойдет.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...