为什么此函数不删除节点?

发布于 2025-01-26 16:32:44 字数 2272 浏览 7 评论 0原文

我是一个初学者的程序员,刚开始用链接列表弄脏我的手。

我目前正在尝试找出一个从“播放列表”(链接列表)删除歌曲(节点)的函数。每个节点都有3个数据点,2个字符串(艺术家和标题)和1个整数(发行年)。有人帮助我找出我在做什么错以及如何解决问题?

函数:

struct Node *borrow_song(struct Node *pointer) {
  
  struct Node *temp = pointer;
  char response[40];
  struct Node *remove;

  printf("Which song do you want to borrow? (title): ");
  scanf(" %s", response);

  
  while(temp != NULL) {
    
    remove = temp;
    
    if (strcmp(response, temp->title) == 0) {
      
      printf("\nSuccess! %s is in the list. Borrowing..\n", response);
      
      free(remove); // I have a feeling this isn't how you properly free a node.
      remove = NULL;
      
        return 0;
      
      }
      
    else 

      temp = temp->next;
    
    }

    printf("%s was not in the list... Try again.", response);

    return 0;

  }

驱动程序:

switch....

case 4:
        borrow_song(head);
        printf("\nNew list:\n\n");
        print_list(head);

驱动器创建功能来自此处的慷慨人(从.txt文件创建节点)

struct Node *read_node(FILE *inputp) {

  struct Node *temp = malloc(sizeof(*temp));
    
  if (temp != NULL &&  fscanf(inputp, "%39s%39s%d", &temp->name, &temp->title, &temp->year) == 3) {

    temp->next = NULL;
    temp->prev = NULL;
    return temp;

    } 

  else {

    free(temp);
    return NULL;

    }
}

,最后,驱动程序:

while ((node = read_node(inputp)) != NULL) {
    
    if (!head) {
      
      head = tail = node;
      
        } 
    
    else {
      
      node->prev = tail;
      tail = tail->next = node;
      
        }
    }

这是输入文件:

  1. Rachmaninov Concerto_no_2 1999
  2. Mozart Symphony_no_41 2000 2000
  3. Vivaldi vivaldi Vivaldi
  4. the_seampon
  5. Vivaldi vivaldi vivaldi vivaldi

这是控制台输出:

您想借哪首歌? (标题):Toccatas

  1. 成功! Toccatas在列表中。借用..
  2. 新列表:
  3. Rachmaninov,Concerto_no_2,1999
  4. Mozart,Symphony_no_41,2000
  5. Vivaldi,The_seastorm,2003年
  6. Beethoven,Symphony_no_5,1994`ʣT,TOCCATAS,TOCCATAS
  7. ,TOCCATAS,TOCCATAS,2005年

仍然在Pointer上工作,我猜我们都在某个地方工作:P

您对您有任何帮助!

I'm a beginner programmer just starting to get my hands dirty with linked lists.

I'm currently trying to figure out a function that deletes a song (node) from a "playlist" (linked list.) Each node has 3 data points, 2 strings (artist and title) and 1 integer (release year.) Can anybody help me figure out what I'm doing wrong and how I can fix it?

Function:

struct Node *borrow_song(struct Node *pointer) {
  
  struct Node *temp = pointer;
  char response[40];
  struct Node *remove;

  printf("Which song do you want to borrow? (title): ");
  scanf(" %s", response);

  
  while(temp != NULL) {
    
    remove = temp;
    
    if (strcmp(response, temp->title) == 0) {
      
      printf("\nSuccess! %s is in the list. Borrowing..\n", response);
      
      free(remove); // I have a feeling this isn't how you properly free a node.
      remove = NULL;
      
        return 0;
      
      }
      
    else 

      temp = temp->next;
    
    }

    printf("%s was not in the list... Try again.", response);

    return 0;

  }

Driver:

switch....

case 4:
        borrow_song(head);
        printf("\nNew list:\n\n");
        print_list(head);

Node creation function from a generous person on here (creates node from .txt file)

struct Node *read_node(FILE *inputp) {

  struct Node *temp = malloc(sizeof(*temp));
    
  if (temp != NULL &&  fscanf(inputp, "%39s%39s%d", &temp->name, &temp->title, &temp->year) == 3) {

    temp->next = NULL;
    temp->prev = NULL;
    return temp;

    } 

  else {

    free(temp);
    return NULL;

    }
}

And lastly, the driver for that:

while ((node = read_node(inputp)) != NULL) {
    
    if (!head) {
      
      head = tail = node;
      
        } 
    
    else {
      
      node->prev = tail;
      tail = tail->next = node;
      
        }
    }

This is the input file:

  1. Rachmaninov Concerto_No_2 1999
  2. Mozart Symphony_No_41 2000
  3. Vivaldi The_Seasons 2003
  4. Beethoven Symphony_No_5 1994
  5. Bach Toccatas 2005

This is the console output:

Which song do you want to borrow? (title): Toccatas

  1. Success! Toccatas is in the list. Borrowing..
  2. New list:
  3. Rachmaninov, Concerto_No_2, 1999
  4. Mozart, Symphony_No_41, 2000
  5. Vivaldi, The_Seasons, 2003
  6. Beethoven, Symphony_No_5, 1994
  7. `ʣt, Toccatas, 2005

Still working on pointers, I guess we all start somewhere :P

Thank you for any help!

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

难以启齿的温柔 2025-02-02 16:32:44

您需要通过将上一个节点的下一个指针设置为删除节点来取消链接节点。如果要删除的节点是列表中的第一个节点,则没有以前的节点,因此您需要允许列表的头更改,这可能是始终将指针返回到HEAD元素(这似乎是如果您查看返回类型!)。

最统一的方法是将node ** Next_ptr最初设置为& Pointer。在循环中,设置node *temp = *next_ptr,查看是否要删除temp node。如果是这样,设置*next_ptr = temp-> next,免费temp和返回指针。如果不是,请设置next_ptr =& temp-> next,然后再次绕过循环。如果temp == null,则找不到节点,应返回指针。这样,如果要删除的节点是第一个,则您将已更新Pointer,否则您将更新上一个节点的Next。无论哪种方式,您始终返回指针,这将永远是头部元素。

You need to unlink the node by setting the previous node's next pointer to point to the node after the one being removed. If the node to remove is the first node in the list, there is no previous node, so you need to allow for the head of the list to change, probably by always returning the pointer to the head element (which appears to be what was intended if you look at the return type!).

The most uniform way to do this is to keep a Node **next_ptr initially set to &pointer. In the loop, set Node *temp = *next_ptr and see if you want to remove the temp node. If so, set *next_ptr = temp->next, free temp and return pointer. If not, set next_ptr = &temp->next and go around the loop again. If temp == NULL, then you didn't find the node, and should return pointer. In this way, if the node to remove is the first one, you will have updated pointer, otherwise you will have updated the previous node's next. Either way, you always return pointer, which will always be the head element.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文