c - 作为函数返回的指针不会像声称的那样被覆盖

标签 c function pointers return

有人声称,由于前面的PrintHelloWorld(),这里的代码不会返回正确的“Sum”。正在执行并替换指针 *ptr 的值指着。但是,每次运行它时我都会得到正确的值,甚至运行 PrintHelloWorld()在打印 *ptr 之前运行十几次或更多次。

那么为什么即使指针指向一个已从堆栈中弹出的值,我的代码仍然可以工作并返回该值?

#include <stdio.h>
#include <stdlib.h>

void PrintHelloWorld()
{
    printf("Hello World\n");
}

int *Add(int *a, int *b)
{
    int c = (*a) + (*b);
    return &c;
}

int main()
{
    int a = 2, b = 4;
    int *ptr = Add(&a,&b);
    PrintHelloWorld();
    printf("Sum = %d\n", *ptr);

    return 0;
}

最佳答案

这就是 Undefined Behavior而且它是未定义的,因此任何事情都可能发生,您实际上无法预测行为,因为它取决于程序的结构及其运行条件。

如果启用编译警告,编译器必须警告您错误,返回局部变量的地址并尝试读取其内容是未定义的行为,因为当您从函数返回时它已经被释放。

由于它是未定义的行为,所以任何事情都可能发生,例如,它可以“正确地工作”。

您正在返回局部变量的地址。变量c存储 *a + *b 的结果的位置是函数 Add() 的本地函数并且具有自动存储期限。

这意味着,当函数返回时,它会被释放。由于您将地址返回给它,并且它已被释放,因此尝试打印它只会输出垃圾。

试试这个看看

int *Add(int a, int b, int *c)
 {
    *c = a + b;
    return c;
 } 

然后在 main()

int main()
 {
    int a = 2, b = 4, c, *ptr;
    ptr = Add(a, b, &c);
    printf("Sum = %d\n", *ptr);

    return 0;
 }

如您所见,您通过了 c的地址并在 Add() 里面修改它功能。

c变量是 main() 的局部变量因此将其地址传递给 Add()修改它,然后在 main() 中读取它完全没问题,因为在main()中它仍然有效。

只有当它超出范围时才会被释放,但在本例中没有发生这种情况。

关于c - 作为函数返回的指针不会像声称的那样被覆盖,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29724277/

相关文章:

c - 在 C 文件中找不到头文件中定义的结构

c - 当我尝试从一串字符中获取数字时,函数总是返回零

php - wordpress - functions.php - preg_replace - <div<-tags

pointers - 将字符串指针转换为空字符串为nil的字符串

c - 使用 C 将 CSV 文件解析为结构并按字母顺序排序

python - PyCharm 警告局部变量可能被引用

c++ - CURLOPT_WRITEFUNCTION 指向成员函数的指针

c - XML 解析启动处理程序中的指针值已更改

c - 是否可以仅使用指向结构的指针(无数据类型)来实现堆栈?

python - HTTP POST Azure 中的授权 header [错误代码 401]