Ошибка сегментации без "const char *" - PullRequest
1 голос
/ 24 декабря 2011

У меня есть вопрос.Я пробую этот код и получаю ошибку «Ошибка сегментации»:

#include <iostream>
#include <cstring>
#include <cctype>

using namespace std;

struct Stack {
    int value;
    Stack *next;
};

void push(Stack* top, int value) {
    Stack *ntop = new Stack;
    ntop->value = top->value;
    ntop->next = top->next;
    top->next = ntop;
    top->value = value;
}

int pop(Stack* top) {
    int val = top->value;
    top->value = top->next->value;
    top->next = top->next->next;
    return val;
}

int main()
{
    Stack *top;
    top->next = NULL;
    push(top, 20);
    cout << pop(top);
}
[10:40:46] [~] >> g++ 3.cpp -o 3 && ./3
Segmentation fault

, но если я добавлю const char * test = ""; до Stack * top; работает нормально:

int main()
{
    const char* test = "";
    Stack *top;
    top->next = NULL;
    push(top, 20);
    cout << pop(top);
}
[10:47:33] [~] >> g++ 3.cpp -o 3 && ./3
20

где моя ошибка?

Ответы [ 4 ]

4 голосов
/ 24 декабря 2011

Проблема здесь:

Stack *top;
top->next = NULL;

Вы ссылаетесь на неинициализированный указатель. Это неопределенное поведение. Так что может случиться что угодно, и это может не соответствовать окружающему коду.

Полагаю, вы забыли что-то выделить для top.

int main()
{
    Stack *top = new Stack;  //  Allocate

    top->next = NULL;
    push(top, 20);
    cout << pop(top);

    delete top;   //  Free

    return 0;
}

* Хотя я хотел бы отметить, что у вас все равно будут утечки памяти внутри кода.

2 голосов
/ 24 декабря 2011
int main()
{
    Stack *top;
    top->next = NULL;

Если бы это был необработанный C, вы бы записали NULL в мусорное хранилище - переменная top не была инициализирована, поэтому она указывает на мусор.->next будет следовать вашему указателю мусора и затем записывать в него со смещением в 4 или 8 байтов.Все еще мусор.

Может быть, C ++ делает магическую struct == class магическую инициализацию для вас - я недостаточно хорошо знаю C ++, чтобы комментировать, - но вы, вероятно, все еще смотрите на мусор.

Добавление test = "" меняет структуру памяти настолько, что вы перезаписываете то, что находится в адресном пространстве вашего процесса.Это все еще мусор, так что кто знает, что вы сломали :), но он не сразу вылетел.

Инициализируйте вашу переменную top чем-то:

Stack *top;
top = malloc(sizeof Stack);
if (!top) {
    /* die */
}
1 голос
/ 24 декабря 2011

Изменить Stack *top на Stack *top = new Stack().

#include <iostream>
#include <cstring>
#include <cctype>

using namespace std;

struct Stack {
    int value;
    Stack *next;
};

void push(Stack* top, int value) {
    Stack *ntop = new Stack;
    ntop->value = top->value;
    ntop->next = top->next;
    top->next = ntop;
    top->value = value;
}

int pop(Stack* top) {
    int val = top->value;
    top->value = top->next->value;
    top->next = top->next->next;
    return val;
}

int main()
{
    Stack *top = new Stack();
    top->next = NULL;
    push(top, 20);
    cout << pop(top);

    return 0;
}
1 голос
/ 24 декабря 2011

Вы не выделили никакой памяти для top. Выделение памяти решит проблему (не забудьте освободить ее, когда закончите). Добавление const char *, вероятно, просто маскирует проблему, помещая в стек другую переменную (это очень случайно и зависит от компилятора, что фактически делает проблему решаемой).

...