С ++ неуловимая ошибка сегментации - PullRequest
2 голосов
/ 18 июля 2011

Я работаю над этим фрагментом кода, и у меня постоянно возникает ошибка сегментации.Что касается жизни, я не могу понять, почему, я знаю, что ошибка сегментации - это когда вы пытаетесь следовать нулевому указателю, но дело в том, что в моем коде «u-> previous» не равно NULL, и «u», япроверено.Если я изменю условие в цикле while на (u! = NULL), оно дважды выполнит итерацию, прежде чем произойдет сбой в «u-> isGreen». Еще раз я проверил каждую итерацию, чтобы определить, не было ли u нулевым.

int extractOptimalPath() {
    Node *u = nodes[NUM_NODES - 1];

    int i = 0;
    while (u != NULL) {
        cout << i << endl;
        u->isGreen = true;
        u = u->previous;
        i++;
    }
    return 0;
}

"node" - это массив указателей на фактические объекты Node.Я точно знаю, что «u-> previous» существует в моих узлах, а «isGreen» инициализируется как false;

Это класс Node, если вы хотите увидеть, что:

class Node {
    public: 
        GLfloat x, y, z;
        int numLinks;
        Node *link1;
        Node *link2;
        GLfloat distance;
        Node *previous;
        bool isGreen;

        Node(GLfloat x, GLfloat y, Node *link1, Node *link2);
        Node(GLfloat x, GLfloat y, Node *link1);
        Node();
        Node(GLfloat x, GLfloat y);
        ~Node();

        bool dijkstra(Node* graph[], Node *source, Node *target); //returns true if a path to target is found
        int dist(Node *n1, Node *n2);
        int extractOptimalPath(Node* graph[]);
};

Что может быть причиной ошибки сегмента?

Ответы [ 4 ]

7 голосов
/ 18 июля 2011

Эта ошибка не , а для нулевых указателей, это указатель, указывающий на что-либо недопустимое. Это может быть нулем, но это также может быть память, которая была освобождена.

4 голосов
/ 18 июля 2011

Я не вижу конструктора копирования в Node, а вижу указатели и деструктор.Итак, вы нарушили Правило Трех .

. В результате, если вы случайно скопируете Узел, деструктор этой копии приведет к эффектам, которые вы видите сейчас.

Обновление: Чтобы быстро проверить это, добавьте конструктор личных копий в класс Node, например:

class Node {
...

private:
  Node(const Node&);
};

Если вы получаете ошибки компилятора сейчас, вы делаете копии.Компилятор укажет вам места, где это происходит.

0 голосов
/ 18 июля 2011

Я предполагаю, что в вашем конструкторе объекта Node предыдущий указатель никогда не устанавливается в NULL в любой точке.Вы должны иметь точку, когда предыдущий установлен в NULL (в вашем фактическом коде, не думайте, что код делает это автоматически).Также, в качестве подсказки, попробуйте использовать gdb для пошагового выполнения кода .Другой совет, valgrind , обычно используется для проверки утечек памяти, но я также использовал его для успешного определения ошибок segfaults.

0 голосов
/ 18 июля 2011

Вам не нужно иметь нулевой указатель, чтобы иметь ошибку сегментации, это происходит каждый раз, когда вы обращаетесь к памяти из разрешенной области.Проверьте поток Что такое ошибка сегментации? .

Ваш код не может сказать, что вызывает ошибку сегмента.Скорее всего, u->previous в одном из ваших узлов указывает на какое-то более или менее случайное место в памяти, но это только предположение.

...