【问题标题】:Segmentation fault using pointers使用指针的分段错误
【发布时间】:2020-12-08 06:41:25
【问题描述】:

嗨,我正在为表示为树的堆编写一些函数。 我的节点是一个结构:

template<typename Object>
struct Node
{
    Node * parent = nullptr;
    Object name;
    Node * left = nullptr;
    Node * right = nullptr;

    Node(Object n) : name(n){}
};

而我的类有一个私有变量叫做root,它是树的根。以下是导致问题的函数,特别是 insert_spot:

template<typename Object>
void MyPriorityQueue<Object>::insert(const Object & elem) 
{
    Node<Object> n_node = Node(elem);
    Node<Object> * new_node = &n_node;
    if (cur_amount > level_amount)
    {
        cur_amount = 1;
        level += 1;
        level_amount += level_amount;
    }
    if (root == nullptr)
    {
        root = new_node;
        cur_amount += 1;
        cur_size += 1;
        if (cur_amount > level_amount)
        {
            cur_amount = 1;
            level += 1;
            level_amount += level_amount;
        }
        return;
    }
    
    insert_spot(new_node); //insert node at bottom
}

而 insert_spot 是:

void insert_spot(Node<Object> * new_node)
    {
        Node<Object> * parent_node = root;
        unsigned temp_amount = cur_amount;
        while (temp_amount > 2)
        {
            temp_amount -= temp_lvl_amount;
        }
        if(temp_amount == 1)
        {
            parent_node->left = new_node;
        }
        else{parent_node->right = new_node;}
        
        new_node->parent = parent_node;
        cur_amount += 1;
        cur_size += 1;
    }

我知道问题是什么,在 insert_spot 函数中,当我尝试执行 parent_node->left = new_node 或 parent_node->right = new_node 时,会出现分段错误。 1如果我将其替换为(并且说对象类型是 int)

Node<Object> n_node = Node(5)
parent_node->left = &n_node;

与 parent_node-> 相同,然后它工作正常。

我之前的代码工作正常,使用“new”运算符创建指针,但由于后来的一些障碍,我不能在这里使用它。

我认为问题出在 'const Object & elem' 上,但我真的不知道为什么我不能做 parent_node->left = new_node 或 parent_node->right = new_node。

也只是来自 main 的示例输入:

MyPriorityQueue<int> test;
test.insert(5);
test.insert(4);

我不是在寻找具体的答案,只是想了解为什么 parent_node-> 会导致分段错误。

【问题讨论】:

    标签: c++ pointers


    【解决方案1】:

    这与Object无关。

    这段代码

    Node<Object> n_node = Node(elem);
    parent_node->left = &n_node;
    

    会很快导致未定义的行为。一旦退出insert 函数,n_node 对象就会被销毁。这意味着您的树持有一个指向已被破坏的对象的指针。任何取消引用该指针的尝试(例如parent_node-&gt;)都会导致未定义的行为。

    无论您在使用 new 时遇到什么问题,您都必须克服它们。 new(或等效的)是这里需要的。您不能使用指向局部变量的指针来构造树。

    关于new 的全部意义在于,使用它创建的对象在退出创建它们的作用域时不会被销毁。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2017-03-10
      • 2016-01-02
      • 1970-01-01
      • 1970-01-01
      • 2010-10-21
      • 1970-01-01
      • 1970-01-01
      • 2013-09-18
      相关资源
      最近更新 更多