C - 将新数据附加到链接列表也会更改以前的数据

时间:2016-12-10 14:15:04

标签: c variables pointers memory linked-list

我是C的新手并且偶然发现了一个我希望你可以帮助我的问题。

我们有一个双链表

struct LinkedList {
    LinkedListNode *first;
    LinkedListNode *last;
};

和作为其中元素的节点

struct LinkedListNode {
    LinkedListNode *previous;
    LinkedListNode *next;
    char *data;
};

尝试将元素附加到列表中,我编写了一个函数,该函数使用给定数据在列表末尾创建节点。

void append(LinkedList *list, char *data)

如果我调用这样的函数,它可以正常工作:

append(list, "abc");
append(list, "def");

导致链接列表包含2个节点 - 第一个数据为"abc",第二个数据为"def"

但是,如果我将数据作为变量传递,例如使用

char testData[10] = "";
strcpy(testData, "abc");
append(list, testData);
strcpy(testData, "def");
append(list, testData);

结果是2个链表节点都具有数据"def"

原因可能是第一个和第二个节点内的数据指针都指向同一个内存,但是,我不知道如何改变这个事实或如何规避它。

我在函数中传递数据的代码如下所示:

struct LinkedListNode *newNode = malloc(sizeof(struct LinkedListNode));
newNode->data = data;

我希望你能帮助我,并提前感谢。

1 个答案:

答案 0 :(得分:3)

该列表仅将指针存储到数据中。在第一个示例中,指向字符串文字的指针是不同的,但在第二个示例中,它们都指向数据发生变化的相同位置。

也许你可以试试

char testData[10] = "";
strcpy(testData, "abc");
append(list, strdup(testData));
strcpy(testData, "def");
append(list, strdup(testData));

但请记住strdup分配了稍后需要释放的内存。

另一种方法是复制函数中的字符串,但如果传递的字符串已经是唯一的,则会创建冗余。

newNode->data = strdup(data);

虽然函数strdup在许多库中,但它不是标准的,但很容易创建自己的(感谢David Bowling)。