我不明白为什么我不能像这样在最后添加节点

时间:2019-12-24 00:14:14

标签: c list struct linked-list

我正在尝试在列表末尾插入一个新节点。我知道第一种方法是“正确的方法”。 但是我正在尝试使用另一个功能(第二个功能)的另一种方法,但是似乎列表没有变化,有什么想法吗?

typedef struct listnode *listptr;

struct listnode {
    int value;
    listptr next;
};

void insert_at_end(listptr *x, int n) {
    while ((*x) != NULL) {       
        x = &((*x)->next);   
    }                       
    *x = (listptr)malloc(sizeof(struct listnode));  
    (*x)->next = NULL;   
    (*x)->value = n;    
}

void insert_at_end_2(listptr x, int n) {
    listptr newnode = (struct listnode *)malloc(sizeof(struct listnode));
    newnode->next = NULL;
    newnode->value = n;

    while (x != NULL) {
        x = x->next;
    }
    x = newnode;
} 

2 个答案:

答案 0 :(得分:0)

此函数的实现有两个问题。

第一个是该函数处理作为参数传递给该函数的原始节点的副本。因此,更改副本不会影响原始参数。

第二个问题是在循环之后

while (x!=NULL){
    x = x->next;
}

x将等于NULL。所以下一条语句

x =newnode;

不会更改最后一个节点的下一个数据成员。因此列表将保持不变。

在未通过引用传递头节点的情况下,使用该方法可以实现以下功能。

listptr insert_at_end_2( listptr x, int n )
{
    listptr newnode = malloc( sizeof( *listptr ) );

    if ( newnode != NULL )
    {
        newnode->next = NULL;
        newnode->value = n;

        if ( x == NULL )
        {
            x = newnode;
        }
        else
        {
            listptr current = x;

            while ( current->next != NULL )
            {
                current = current->next;
            }
            current->next  = newnode;
        }
    }

    return x;
} 

但是,这种实现方式(如头节点通过引用传递时的第一种实现方式)有一个缺点:该函数不会报告是否成功分配了新节点。

因此该函数的更好实现看起来像

int insert_at_end( listptr *x, int n )
{
    listptr newnode = malloc( sizeof( *listptr ) );

    int success = newnode != NULL;

    if ( success )
    {
        newnode->next  = NULL;   
        newnode->value = n;

        while ( *x != NULL )
        {       
            x = &( *x )->next;   
        }                       

        *x = newnode;
    }

    return success;  
}

答案 1 :(得分:0)

@来自莫斯科的弗拉德 我使您的代码类似于我的代码。所以这行得通。


void insert_at_end_2( listptr x, int n )
{
  listptr newnode =  (listptr)malloc( sizeof( listptr ) );
  newnode->next = NULL;
  newnode->value = n;


  while ( x->next!= NULL )
  {
      x = x->next;
  }
  x->next  = newnode;

}