我一直收到以下错误:分段错误(核心已转储)。我发现了导致问题的代码行(在程序内部以注释标记)。请告诉我为什么会发生此错误,以及如何解决该错误。
我试图使我的代码(在纸上)空运行,但从我的理解来看,没有逻辑错误。
我只是最近才开始编码和stackoverflow,请引导我逐步解决问题以及代码。谢谢!
class tree
{
struct node // Creates a node for a tree
{
int data;
bool rbit,lbit; // rbit/lbit= defines if right/left child of root is present or not
node *left,*right;
};
public:
node *head,*root;
tree() // constructor initializes root and head
{
root=NULL;
head=createnode(10000);
}
node *createnode(int value)
{// Allocates memory for a node then initializes node with given value and returns that node
node *temp=new node ;
temp->data=value;
temp->lbit=0;
temp->rbit=0;
temp->left=NULL;
temp->right=NULL;
return temp;
}
void insert(node *temp,int value) // Creates binary search tree node by node
{
if(root==NULL) // Checking if tree is empty
{
root=createnode(value); //Root now points to new memory location
head->left=root;
head->lbit=1;
root->left=head;//this line gives the segmentation fault (what i thought before correction)
}
}
void inorder(node *root) // Inorder traversal of tree (this function is logically incorrect)
{
if(root==NULL)
return;
inorder(root->left);
cout<<root->data<<"\t";
inorder(root->right);
}
void getdata()//Accepts data , creates a node through insert() , displays result through inorder()
{
int data;
cout<<"Enter data"<<endl;
cin>>data;
insert(root,data);
inorder(root);
}
/*void inorder(node *root) // Working inorder code
{
if(root->lbit==1)
inorder(root->left);
cout<<root->data<<"\t";
if(root->rbit==1)
inorder(root->right);
}*/
};
int main()
{
tree t; // Tree Object
t.getdata(); // Calling getdata
return 0;
}
答案 0 :(得分:3)
我认为评论部分主要反映了误解。很容易相信您在特定行上 ON 遇到了崩溃。
实际上并非如此。取而代之的是,您在树中创建了一个循环,该循环导致inorder
函数导致无限递归。这会导致堆栈溢出并导致段错误-如果您只是在连接了调试器(例如gdb)的情况下运行程序,这将非常容易发现。
temp = createnode(value);
if(root == NULL)
{
root = temp;
head->left = root;
head->lbit = 1;
temp->left = head;
}
看看刚才创建的循环:
head->left points to root
root->left == temp->left, which points to head
现在将遍历有序遍历:
root
head
root
head
root
head
...
由于它永远不会到达左分支的末尾,因此该函数在溢出堆栈和崩溃之前永远不会输出任何内容。
因此,您的代码在逻辑上不正确。其中存在一个基本的设计缺陷。您需要重新考虑树中存储的内容以及原因。
答案 1 :(得分:1)
从代码中
root=temp; //Root now points to temp
head->left=root;
head->lbit=1;
temp->left=head;// this line gives the segmentation fault
根未指向temp。 temp(pointer)被分配给root(pointer)。 head的左指针是root,而temp的左指针是head(这意味着root的左指针是head)。因此在函数“顺序”中,
void inorder(node *root) // Inorder traversal of tree
{
if(root==NULL) <<<<<<
return;
inorder(root->left);
cout<<root->data<<"\t";
inorder(root->right);
}
参数节点* root(左)从不为NULL,函数从不返回。
答案 2 :(得分:0)
没有确切的信息(例如node.lbit
)。
问题的insert()
函数将不起作用。它传递的值会立即被覆盖(以及其他问题)。 tree.head
的作用没有说明,因此将其忽略。字段node.lbit
和node.rbit
看起来是node.left != NULL
的多余标志(与右边类似)。这些也被省略。 insert()
也没有正确创建树。
void insert(int value) // Insert a value into the tree (at branch)
{
// Create a new node to insert
struct node *temp = createnode(value);
if (root == NULL) // Checking if tree is empty
{
root = temp; //Root now points to temp
}
else
{
insertAtBranch(root, temp);
}
}
// recursively find the leaf-node at which to insert the new node
void insertAtBranch(node *branch, node *new_node)
{
// to create a BST, less-than go left
if (new_node->value <= branch->value)
{
if (branch->left == NULL)
branch->left = new_node; // There's no left-branch, so it's the node
else
insertAtBranch(branch->left, new_node); // go deeper to find insertion point
}
else // greater-than go right
{
if (branch->right == NULL)
branch->right = new_node;
else
insertAtBranch(branch->right, new_node);
}
}
想象一下二叉树如何工作。新节点只能插入到边缘。因此,您查看一个给定的节点,并确定该新节点是否小于或小于您正在查看的节点(当然,除非树为空)。
假设new-node.value
小于branch-node.value
,您想向左分支。仍然具有相同的节点,如果它没有左分支(node.left == NULL)
,则新节点是的左分支。否则,您需要沿着左分支行驶并再次检查。
我本可以将node
设为一个类,并使用构造函数至少设置默认属性和value
。但这没什么大不了的。