未定义的动作?程序一个接一个地打印出不同的值
Undefined action? Program prints out different values one after the other
我不太清楚如何描述这个问题 - 以及我的错误是否有任何名称。
当我运行程序时输入一些数字,例如5 tree.root->pocz 首先是 1,然后是奇怪的数字。任何人都知道这是怎么回事以及如何修复它?
struct Node
{
int pocz;
int kon;
Node *left, *right, *up;
};
class AVL{
public:
Node *root;
void initiate(){
root = NULL;
}
bool insertNode(int poczPrz, int konPrz);
};
AVL tree;
//part of AVL insert function
bool AVL::insertNode(int poczPrz, int konPrz){
Node w;
w.pocz = poczPrz;
w.kon = konPrz;
Node *n = &w;
Node *x = tree.root;
Node *y, *z;
y = n->left = n->right = NULL;
while(x){
if(x->pocz == n->pocz){
delete n;
return false;
}
y = x;
x = (n->pocz < x->pocz) ? x->left : x->right;
}
if(!(n->up = y)){
cout << "We leave the function here\n";
tree.root = n;
return true;
}
if(n->pocz < y->pocz) y->left = n;
else y->right = n;
}
int main()
{
int n; cin >> n;
tree.initiate();
tree.insertNode(1,n);
cout <<"root->pocz: "<< tree.root->pocz <<endl; //prints 1
cout <<"root->pocz: "<< tree.root->pocz <<endl; //now prints sth like 2306050
return 0;
}
在 insertNode
中,您的 w
对象具有自动存储,n
是指向它的指针。在对该函数的调用中,它将分配 tree.root = n;
。在函数 returns 之后对象被销毁并且指针 tree.root
悬空(指向释放的内存)。在那之后,取消引用诸如 tree.root->pocz
之类的悬垂指针将具有未定义的行为。您可以通过动态分配节点来解决这个问题。
主要问题是n指向函数insert中的局部变量w。在函数 insert 结束时,w 被自动删除。树中的指针指向一个空位置。在您的第一个 cout 指令中,碰巧没有任何内容覆盖 w 的先前内存位置。因此它打印 1。该内存位置随后被其他东西(来自 cout 调用)覆盖,因此它打印垃圾。
现在解决方法,使用Node *n = new Node;而不是将其设置为 &w.
我不太清楚如何描述这个问题 - 以及我的错误是否有任何名称。
当我运行程序时输入一些数字,例如5 tree.root->pocz 首先是 1,然后是奇怪的数字。任何人都知道这是怎么回事以及如何修复它?
struct Node
{
int pocz;
int kon;
Node *left, *right, *up;
};
class AVL{
public:
Node *root;
void initiate(){
root = NULL;
}
bool insertNode(int poczPrz, int konPrz);
};
AVL tree;
//part of AVL insert function
bool AVL::insertNode(int poczPrz, int konPrz){
Node w;
w.pocz = poczPrz;
w.kon = konPrz;
Node *n = &w;
Node *x = tree.root;
Node *y, *z;
y = n->left = n->right = NULL;
while(x){
if(x->pocz == n->pocz){
delete n;
return false;
}
y = x;
x = (n->pocz < x->pocz) ? x->left : x->right;
}
if(!(n->up = y)){
cout << "We leave the function here\n";
tree.root = n;
return true;
}
if(n->pocz < y->pocz) y->left = n;
else y->right = n;
}
int main()
{
int n; cin >> n;
tree.initiate();
tree.insertNode(1,n);
cout <<"root->pocz: "<< tree.root->pocz <<endl; //prints 1
cout <<"root->pocz: "<< tree.root->pocz <<endl; //now prints sth like 2306050
return 0;
}
在 insertNode
中,您的 w
对象具有自动存储,n
是指向它的指针。在对该函数的调用中,它将分配 tree.root = n;
。在函数 returns 之后对象被销毁并且指针 tree.root
悬空(指向释放的内存)。在那之后,取消引用诸如 tree.root->pocz
之类的悬垂指针将具有未定义的行为。您可以通过动态分配节点来解决这个问题。
主要问题是n指向函数insert中的局部变量w。在函数 insert 结束时,w 被自动删除。树中的指针指向一个空位置。在您的第一个 cout 指令中,碰巧没有任何内容覆盖 w 的先前内存位置。因此它打印 1。该内存位置随后被其他东西(来自 cout 调用)覆盖,因此它打印垃圾。
现在解决方法,使用Node *n = new Node;而不是将其设置为 &w.