过滤链表并返回新的链表C.

时间:2015-07-13 00:30:39

标签: c linked-list hashtable

我正在尝试过滤链接列表。由于我不想更改原始链接列表,因此我想创建一个子链接列表并将其返回。

我遇到了麻烦,因为我只知道如何从过滤过程中获取1个节点,但我不知道如何移动并将原始链表中的节点添加到子链表中。 / p>

我有这样的结构(这表示哈希表中的一个条目):

typedef struct Entry {
   char *word;
   int len;
   struct Entry *next;
} Entry;

我的过滤器函数将接收字长和原始链表作为参数,然后查找具有相同值len的节点。每当它找到具有相同len值的节点时,它就会将该节点添加到另一个链表。最后它返回新的链表。

struct Entry* filterLen(int len, struct Entry *en) {
   struct Entry *temp = (struct Entry *)malloc(sizeof(struct Entry));

   while(en->next != NULL) {
      if (en->len == len) {
         // assign values to temp list
         temp->word = en->word;
         temp->len = en->len;
         temp->next = en;
      }

      en = en->next; // move through list
   }

   return temp;
}

4 个答案:

答案 0 :(得分:2)

Entry* filterLen(int len, Entry *en) {
   Entry *result = NULL, **temp = &result;

   while(en != NULL) {
      if (en->len == len) {
     // assign values to temp list
         *temp = malloc(sizeof(Entry));
         (*temp)->word = en->word;
         (*temp)->len = en->len;
         (*temp)->next = NULL;
         temp = &((*temp)->next);
      }

      en = en->next; // move through list
  }

  return result;
}

EDIT 这里似乎是一场比赛,所以:

Entry* filterLen(int len, Entry *en) {
   Entry *result, **temp = &result;

   for ( ; en; en = en->next) { // Move through list
      if (en->len == len) {        // Then assign values to temp list
         *temp = malloc(sizeof(Entry));
         (*temp)->word = en->word; // WARNING str shared with en list!!!
         (*temp)->len = en->len;
         temp = &((*temp)->next);
      }
   }
   *temp = NULL;
   return result;
}

答案 1 :(得分:2)

Entry* filterLen(int len, Entry *en) {
    Entry result = { NULL, 0, NULL };
    Entry *curr  = &result;

    while(en != NULL){
        if(en->len == len){
            Entry *temp = malloc(sizeof(*temp));
            *temp = *en;
            temp->next = NULL;
            curr = curr->next = temp;
        }
        en = en->next;
    }
    return result.next;
}

答案 2 :(得分:1)

根据我在您的问题中的理解,您希望返回一个链接的条目列表,其len字段等于输入参数。目前,您的代码只存储一个“temp”,您需要重建一个新列表。

struct Entry* filterLen(int len, struct Entry *en) {
  struct Entry *first = NULL;
  struct Entry *last = NULL;
  while(en != NULL) {
    if (en->len == len) {
      if(last){
        last->next = (struct Entry *)malloc(sizeof(struct Entry));
        last = last->next;
      } else {
        last = (struct Entry *)malloc(sizeof(struct Entry));
        first = last;
      }
      // assign values to temp list
      last->word = en->word;
      last->len = en->len;
      last->next = NULL;
    }
    en = en->next; // move through list
  }
  return first;

}

答案 3 :(得分:1)

现在,您的过滤功能正在将找到的最后一个节点的内容(包括next指针)复制到temp节点中。这导致函数返回最后一个匹配节点加上列表中的任何内容。

每次找到匹配的节点并将内容复制到该节点时,您需要做的是创建一个新节点。这包括重复字符串,因此您不必担心可能会双重释放任何内容。

struct Entry* filterLen(int len, struct Entry *en) {
   struct Entry *result = NULL, *temp = NULL;

   while(en != NULL) {
      if (en->len == len) {
         // copy node to end of temp list
         if (temp == NULL) {
             result =  malloc(sizeof(struct Entry));
             temp = result;
         } else {
             temp->next =  malloc(sizeof(struct Entry));
             temp = temp->next;
         }
         temp->word = strdup(en->word);  // Perform a deep copy
         temp->len = en->len;
         temp->next = NULL;
      }

      en = en->next; // move through list
   }

   return result;
}