指针被分配给错误的局部变量
Pointer is assigned to wrong local variable
我刚刚开始学习 c++,我这里有一些示例代码,显示了局部变量和指针的问题。
#include <iostream>
using namespace std;
int* f1 (int n) {
int* p = &n;
return p;
}//f1
void f2 (int na) {
int nb = na;
}//f2
int main () {
int* nn = f1 (101);
f2 (2002);
cout << *nn << endl;
}//main
/*
2002 // output MinGW 6.2.0
*/
不幸的是,我找不到为什么会发生这种情况的解释。据我了解,p 返回给调用方,所以 nn 应该等于 101,但它以某种方式分配给了赋予 f2 的参数?我真的很困惑。如果这是一个非常基本的问题,我也很抱歉。
此指令:
int* p = &n;
将指针分配给局部自动变量n
。
该变量在f1()
结束时被销毁,因此一旦您执行
return p;
指针变为无效。将其存储在nn
中并通过取消引用来使用指向值*nn
触发未定义的行为- 您无法知道之后会发生什么。
在您的特定情况下实际发生的情况(归功于 @Caleth)可能是n
变量存储在机器堆栈上,然后na
f2()
使用相同的位置,因此它被要f2
的参数的2002
值覆盖。
但永远不要依赖这样的效果!变量不需要以相同的方式分配给不同的函数,例如,堆栈帧可以逐个堆叠,并在以后释放几个后续调用(我在 - IIRC - Watcom C 编译器中见过这样的行为很多年前),或者na
可以在微处理器的寄存器中分配。无论如何,即使它们位于堆栈上并且位于堆栈的同一位置,它们也不需要保持相同的值!该堆栈可以由其他机制使用,不一定在源代码中可见。
附言:
同样的情况发生在C语言中,而不仅仅是在C++中。将cout
与其<<
运算符一起使用在问题中并不重要。
正如 CiaPan 在他/她的回答中指出的那样,一旦你返回指向局部变量的指针,你就处于未定义的行为领域。以下是幕后实际发生的情况:您的局部变量存储在函数调用堆栈中,该堆栈在每次函数调用/返回时都会更改状态。当函数返回时,它通常不会清除它使用的堆栈内存,因此它可能看起来仍然有效。但按照语言标准,这种记忆几乎不复存在,任何指向它的指针都会立即失效。我希望ASCII艺术能帮助你理解到底发生了什么。
Before call of f1():
| main(): nn |
| ?????????? |
|
v
???
During execution of f1():
| main(): nn | f1(): n | f1(): p |
| ?????????? | 101 | &n |
| ^ /
v ________/
???
After f1() returns (nn is invalid as n does not exist anymore):
| main(): nn | unused space |
| invalid | 101 | &n |
^
________/
During execution of f2() (nn is still invalid, but seems to point to na now):
| main(): nn | f2(): na | f2(): nb |
| invalid | 2002 | 2002 |
^
________/
After f2() returns, nn is still invalid, but points to the memory that was once occupied by na:
| main(): nn | unused space |
| invalid | 2002 | 2002 |
^
________/
- 修复未初始化的局部变量错误
- 未初始化的局部变量错误甚至认为我初始化了它(C++)
- 我创建的类似乎错误地设置了它的局部变量
- 分配给静态变量的局部变量;编译错误在'c'但在 C++ 中成功
- 静态局部变量会被错误地优化吗?
- 错误 C4700:使用未初始化的局部变量'result'
- 尝试声明函数的局部变量,但得到范围错误
- 指针被分配给错误的局部变量
- 错误 C4700:使用未初始化的局部变量'enemyHealth'
- 在c++上创建税务计算程序,错误为未初始化的局部变量
- C++错误 C4700:使用未初始化的局部变量'i'
- 我不断收到错误:运行此代码时重新定义'i'。对局部变量的误解
- 从函数中引用局部变量不会给出错误
- 错误 C4700:使用未初始化的局部变量'A'
- C++:使用错误 C4700 未初始化的局部变量""
- 错误 C4700:使用未初始化的局部变量'lowest'
- 错误 1 错误 C4700:未初始化的局部变量'rate'并在C++中'hours'
- 全局变量如何在销毁时产生错误,而局部变量却不会
- 未初始化的局部变量使用错误
- 如何在循环外打印总和?我认为全局变量和局部变量的减速存在一些错误