【问题标题】:New node doesnt get properly added to end of linked list when adding through function通过函数添加时,新节点未正确添加到链表的末尾
【发布时间】:2018-12-04 11:12:48
【问题描述】:

我正在尝试通过添加节点的函数将新节点添加到链表。但是当我打印列表时,似乎所有节点中的数据都被最近添加的数据替换了。

typedef struct things {
    char *string;
    struct things *next;
} something;

void addnode(something **head, char *str);
void printlist(something **head);

int main()
{
    int i;
    char word[50];
    something *head = NULL;

    puts("How many strings?");
    scanf("%d", &i);

    while(i > 0)
    {
        scanf("%49s", word);
        addnode(&head, word);
        i--;
    }

    printlist(&head);
    return 0;
}

void addnode(something **head, char *str)
{
    something *last = *head;
    something *newnode;

    newnode = malloc(sizeof(something));
    newnode->string = malloc(50*sizeof(char));
    newnode->string = str;
    newnode->next = NULL;

    if ((*head)==NULL)
    {
        (*head) = newnode;
        return;
    }
    else
    {
        while(last->next != NULL)
        {
            last=last->next;
        }
        last->next = newnode;
        return;
    }
}
void printlist(something **head) //print contents of list, to check if list was created
{
    puts("print");
    something *current = *head;
    while(current != NULL)
    {
        printf("%s", current->string);
        current=current->next;
    }
}

这就是我想出的。当我输入说5个字onetwothreefourfive,我得到输出five five five five five。这是我尝试打印的方式的问题吗?还是我如何传递指针和链接节点?

【问题讨论】:

  • 你也要复制word的内容。现在它们都指向同一个缓冲区word,因此都将显示相同的值。 :-)
  • newnode->string = malloc(50*sizeof(char)); newnode->string = str; 这不是复制字符串的方法(另外:你在这里泄漏内存)而是使用strcpy()(或strdup()整个字符串)

标签: c singly-linked-list


【解决方案1】:

分配指针不会复制它们的内容。只是让它们指向相同的内存地址。

在您的代码中,您正在为新节点的str 分配内存,并使其指向缓冲区的地址(您的情况为word)。通过这样做,最终所有节点的str 将指向缓冲区最后一个值的地址的内容(您的情况为五个)。

newnode->string = malloc(50*sizeof(char));
newnode->string = str;

这里的另一个问题是您不会根据缓冲区的内容动态分配内存。

要准确分配所需的内存量,请尝试以下操作:

替换:

newnode->string = malloc(50*sizeof(char));

与:

 newnode->string = malloc((strlen(str)+1)*sizeof(char));

使用strlen 可以获得字符数,+1 用于为终止字符'\0' 分配空间。

所以要解决您最初的问题,您需要将缓冲区的内容复制到新分配的内存中:

替换:

newnode->string = str;

strcpy(newnode->string,str);

【讨论】:

  • 请说明使用strlen(str)+1 来分配确切的内存量。
【解决方案2】:

在函数 addnode() 中代替

newnode->string = malloc(50*sizeof(char)); newnode->string = str;

试试

newnode->string = strdup(str);

它应该工作。 :)

【讨论】:

    【解决方案3】:

    更改插入功能,如,

    void addnode(something **head, char *str)
    {
        something *last = *head;
        something *newnode;
    
        newnode = malloc(sizeof(something));
        newnode->string = malloc(50*sizeof(char));
        strcpy(newnode->string, str);
        newnode->next = NULL;
    
        if ((*head)==NULL)
        {
            (*head) = newnode;
            return;
        }
        else
        {
            while(last->next != NULL)
            {
                last=last->next;
            }
            last->next = newnode;
            return;
        }
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-06-14
      • 2020-05-24
      • 1970-01-01
      • 2014-02-02
      • 2013-11-13
      相关资源
      最近更新 更多