地址边界错误 - 为什么链表中的节点没有正确添加?

Address boundary error - Why don't the nodes in my linked list get added properly?

提问人:user21025014 提问时间:1/25/2023 更新时间:1/27/2023 访问量:52

问:

我正在尝试用 C 语言实现链表,但是我似乎无法弄清楚如何将元素附加到列表中。

#include <malloc.h>
#include <stdio.h>
#include <stdlib.h>

typedef struct element {
    int value;
    struct element* next;
} element;

typedef struct list {
    element* head;
} list;

list* createList(int headValue) {
    list* L = malloc(sizeof(list));
    L->head = malloc(sizeof(element));
    L->head->value = headValue;
    L->head->next = NULL;
    return L;
}

// Returns the new length of the list
int appendToList(list* L, int value) {
    element* first = L->head;
    element* current = first;
    int length = 1;
    
    if (first == NULL) {
        printf("first is NULL\n");
        exit(2);
    }
    while (current != NULL) {
        current = current->next;
        length++;
    }
 
    current = malloc(sizeof(element));
    current->next = NULL;
    current->value = value;
    length++;

    return length;
}

// returns the value at index N (zero based)
//
// If the list has < N elements, returns -1 
int getAtIndexN(list* L, int N) {
    element* current = L->head;
    for (int i=0; i<N; i++) {
        if (current->next == NULL) {
            printf("unable to get to index %d\n", i+1);
            exit(1);
        }
        current = current->next;
    }
    return current->value;
}

int main(int args, char** argv) {
    int initvalues[] = {1,3,4,4};
    list* L = createList(5);
    for (int i=0; i<4; i++) {
        appendToList(L, initvalues[i]);
    }
    
    printf("element at index 1 has value %d\n", L->head->next->value);
    return 0;
}

我调用了 4 次,以便将值附加到列表中,但似乎只有列表的头部被正确添加到列表中。in 的结果为 。我不确定问题出在其他地方还是其他地方。appendToListinitvaluesprintfmain'./a.out' terminated by signal SIGSEGV (Address boundary error)appendToList

c 指针 链接列表 malloc

评论

1赞 Support Ukraine 1/25/2023
看来应该是 但是还有更多的事情需要解决......喜欢应该是,还有更多......(你应该能够从这里修复它)while (current != NULL) {while (current->next != NULL) {current = malloc(sizeof(element));current->next = malloc(sizeof(element));
0赞 M Oehm 1/25/2023
在循环中,最终将为 null,并且您丢失了对原始列表的引用。接下来的一切,分配和同化都是孤立发生的,除了泄漏内存之外没有任何效果。while (current != NULL)currentcurrent?
0赞 Support Ukraine 1/25/2023
OT:既然你有一个(包含)并且你想添加到列表的末尾,你应该考虑在 中也有一个指针。它添加了更多的控制代码,但它使追加速度更快。struct listheadtailstruct list
1赞 John3136 1/25/2023
看起来 appendToList 创建了新节点,但没有指向它的任何内容 (something->next = new_node)。
1赞 Support Ukraine 1/25/2023
OT:IMO 这是一个糟糕的设计,将第一个节点添加到列表中。它应该只创建一个空列表,即 换句话说,您的代码应该能够处理空列表。您当前的代码不允许这样做。createListL->head = NULL

答:

1赞 2 revsuser21025014 #1

在循环中,最终将为 null,并且您丢失了对原始列表的引用。接下来的一切,分配和赋值都是孤立发生的,除了泄漏内存之外没有任何效果。while (current != NULL)currentcurrent?

看来应该是 但是还有更多的事情需要解决......喜欢应该等等。while (current != NULL) {while (current->next != NULL) {current = malloc(sizeof(element));current->next = malloc(sizeof(element));

PS:IMO 这是一个糟糕的设计,将第一个节点添加到列表中。它应该只创建一个空列表,即 L->head = NULL 换句话说,您的代码应该能够处理一个空列表。您当前的代码不允许这样做。createList

评论

0赞 Adrian Mole 1/25/2023
既然你已经承认这篇文章的大部分内容不是你自己的作品,你可以考虑把这个答案写进社区维基