【问题标题】:Insertion into sorted linked list插入排序链表
【发布时间】:2018-11-26 07:51:42
【问题描述】:

我正在尝试将元素添加到已排序的链表中。当我尝试添加一个小于现有元素或小于第一个元素的元素时。它开始重复。有人可以帮我解决这个问题吗?

提前致谢

struct node {
    int key;
    struct node *next;
};

struct node *init() {
    struct node *head = 0;
    return head;
}

void create(struct node **head, int num) {
    struct node *tmp = *head;
    struct node *prev = NULL;
    struct node *new = calloc(1, sizeof(struct node));
    new->key = num;
    prev = tmp;
    if (*head == NULL)
        *head = new;
    while (tmp != NULL && tmp->key < num) {
        prev = tmp;
        tmp = tmp->next;
    }
    new->next = tmp;
    if (prev != NULL)
        prev->next = new;
}

int main() {
    int op;
    int num;
    struct node *head;
    head = init();
    do {
        printf("\n Menu \n 1.Insert \n 2.delete element \n 3.display List 
    \n 4. end program ");
        printf("n \n \n please enter an option :     ");
        scanf("%d", &op);
        switch (op) {
          case 1:
            printf("Enter data:");
            scanf("%d", &num);
            create(&head, num);
            break;
          case 2:
            printf("Enter data:");
            scanf("%d",&num);
            delete(&head, num);
            break;
          case 4:
            free(head);
            exit(0);
          default:
            printf("\n enter an option : ");
        }
    } while(1);
}

这是我得到的:

【问题讨论】:

    标签: c linked-list


    【解决方案1】:

    当你插入一个小于或等于第一个元素的元素时,你永远不会进入 while 循环。因此,执行的代码会在您的列表中创建一个循环,因为 prevtmp 是相同的。

    这是你不进入循环时执行的代码:

    prev = tmp;
    ...
    new->next = tmp;
    if (prev != NULL)
        prev->next = new; // You create the cycle here.
    

    【讨论】:

      【解决方案2】:

      您的create 函数存在多个问题:

      • 应该重命名为 append_node 或更明确的名称。
      • 您应该避免使用 C++ 关键字,例如 newdelete,因为这可能会使一些编辑和读者感到困惑。
      • 你应该测试内存分配失败并返回NULL,否则返回新的节点指针以便调用者测试错误。
      • 你错误处理num小于头节点key的情况: 新节点:你将next指针设置为链表中的前一个节点,也就是头节点,有效地创造了一个循环。

      这是一个更正的版本:

      struct node *append_node(struct node **head, int num) {
          struct node *tmp, *new_node;
      
          new_node = calloc(1, sizeof(*new_node));
          if (new_node == NULL)
              return NULL;
          new_node->key = num;
          tmp = *head;
          if (tmp == NULL || tmp->key > num) {
              /* insert at the head */
              new_node->next = tmp;
              *head = new_node;
          } else {
              /* locate the insertion point */
              while (tmp->next != NULL && tmp->next->key <= num)
                  tmp = tmp->next;
              new_node->next = tmp;
              tmp->next = new_node;
          }
          return new_node;
      }
      

      注意有一个更短的版本使用双指针定位插入点,但是比较难理解:

      struct node *append_node(struct node **head, int num) {
          struct node *new_node;
      
          new_node = calloc(1, sizeof(*new_node));
          if (new_node != NULL) {
              new_node->key = num;
              while (*head != NULL && (*head)->key < num)
                  head = &(*head)->next;
              new_node->next = *head);
              *head = new_node;
          }
          return new_node;
      }
      

      【讨论】:

        猜你喜欢
        • 2011-04-23
        • 1970-01-01
        • 2015-10-16
        • 2016-08-26
        • 1970-01-01
        • 1970-01-01
        • 2018-11-04
        • 1970-01-01
        相关资源
        最近更新 更多