2013-04-09 80 views
3
#include<stdio.h> 

int* a(int* b){ 
int a = 20; 
printf("\n \n"); 
if(a == 20){ 
    printf("\n return from if a : 0x%x \n",a); 
    return &a; 
} 
else{ 
    printf("\n returning from else b : 0x%x\n",b); 
    return b; 
} 
} 

int main(){ 
int n = 10; 
int *k,*m; 
k = &n; 
m = a(k); 
printf("\n m ; 0x%x m : %d \n",m,*m); 
return 0; 
} 

这里我返回返回指针函数的局部变量。在函数退出期间,所有变量都将从堆栈内存中移出,但函数如何仍然保留地址'a'处的值并打印数据?本地变量地址可以保存在返回指针的函数中

O/P:

return from if a : 0xbfd8cf14 

m ; 0xbfd8cf14 m : 20 

的地址被保持在指针m和它正确打印的值。我试过改变不同的号码。

+1

标记为C++,但完全相关:http:// stackoverflow。com/questions/6441218/can-a-local-variables-memory-be-accessible-scope- – chris 2013-04-09 13:38:51

+0

@chris:这个链接有一个很好的解释。谢谢。 – Angus 2013-04-09 13:56:54

+1

酒店房间的答案在这里有点出名。 – chris 2013-04-09 13:58:16

回答

3

通过声明static int a = -1;可以使返回值“可靠”,即使从函数返回后也会使a持续存在......但在很多情况下,这是一个非常糟糕的主意......尤其是如果您将要多线程。

这就是说...返回一个指向临时(本地)变量的指针会在运行时造成严重破坏。所以,你永远不想这么做......你需要将它变成一个静态的本地或找到一个更好的方式来处理它。

扩展回答您的编辑后:当你将-1a作为一个局部变量,你实际上是在堆栈和&a点,该位置上的某个位置存储-1。从函数返回时,堆栈不会被销毁,但行为现在是未定义的,因为当地址是有效指针时,该地址的内容可能已被修改......例如,如果调用另一个函数将数据推入堆栈并/或声明局部变量,它们可能已经覆盖了您所期望的值。另外,谁知道优化器可能注入了什么疯狂。所以......它可能工作如果你碰巧在读取其他东西之前先读取它的值......但是你无法保证它能正常工作,并且它通常会因实现而异。

6

这是你的程序调用未定义的行为。它可以自由地打印任何东西(或崩溃,或做任何想要的)。 (也许这是实际发生的事情:“从记忆中移除”并不意味着持有该变量的记忆被毁灭,置于火中或被魔法师消失,仅仅是因为它失效了,因为它是一个函数内的自动变量,很可能发生的事情只是当函数返回时栈指针被移位,使得该变量无效但完好无损。不要依赖于此)

2

这是一个undefined行为。当你离开函数时,堆栈没有被清理,所以变量的实际值仍然存在,但你不应该访问它。在显示变量的内容之前,尝试调用另一个函数。尝试使用-O3编译可能的不同行为。

3

退出函数后返回的指针将无效。这是一个未定义的行为。

保存的指针指向内存中的一个位置,您无权再读取/写入它。

要保持地址有效,请使用static变量。

static int a = -1; 
// ... 
return &a;