从C中的双向链接列表中删除重复项

时间:2013-04-17 12:08:28

标签: c doubly-linked-list buckets

我正在尝试使用200到800之间的双重SAT成绩列表。我需要从列表中的所有重复项中删除,即确保每个成绩只出现一次,删除所有重复项。

#define HIGHEST_GRADE 800

typedef struct dListNode{
    int* dataPtr;
    struct dListNode* next;
    struct dListNode* prev;
}DListNode;

typedef struct dList

{
    DListNode* head;
    DListNode* tail;
}DList;

void removeDuplicates(DList* lst)
{
    int i;
    int gradesBucket [numOfGrades];
    DListNode* temp;
    temp = lst->head;

    for(i=200 ; i<HIGHEST_GRADE ; i++) /*creating 600 buckets - each bucket for a grade*/
        gradesBucket[i] = FALSE;

    while (temp)
    {
        if ((gradesBucket [*temp->dataPtr]) == TRUE) /*if current grade has already  */
                                                     /* appeared earlier on the list */
        {
            deleteFromList (temp);  /*delete that grade's cell*/
        }
        else
            gradesBucket[*temp->dataPtr] = TRUE; /* mark grade bucket as true, meaning */
                                                 /* the grade already appeared*/
        temp = temp->next; /*moving on to next grade*/
    }
}

void deleteFromList(DListNode*  toRemove)
{
    toRemove->prev->next = toRemove->next;
    toRemove->next->prev = toRemove->prev;

    deAllocateListCell (toRemove);    
}

void deAllocateListCell (DListNode* cell)
{
    free (cell->dataPtr);
    free (cell);
}

请帮我理解错误。


这是固定代码,但仍然无法正常工作。现在它编译但屏幕上没有显示任何内容。顺便说一下,我不需要注意删除头部,因为第一个数字永远不会重复......但是如果头部为NULL则我会处理它;
我还将我要删除的单元格的前一个单元格发送到函数deleteFromList。它仍然无法正常工作。有任何想法吗?谢谢!

    void deleteFromList(DList* lst, DListNode*  p)
{

DListNode* del_cell = p->next;   /* cell to delete*/

if (p->next->next == NULL) /*if cell to remove is the tail*/
{
    deAllocateListCell (p->next); /* freeing current tail */
    lst->tail = p;  /* p is the new tail */
    p->next = NULL; /* tail points to NULL */
}
else /* if cell to remove is not the tail (note: can't be head beacuse no duplicates can be found in the first grade) */
{
    p->next = del_cell->next;
    del_cell->next->prev = p;
    deAllocateListCell (del_cell);
    }
}

3 个答案:

答案 0 :(得分:1)

函数deleteFromList()的代码不考虑(字面)边缘情况:删除列表的第一个或最后一个节点。

另外,您的代码取消引用指向解除分配节点的指针;指针可能变得完全无效,或者free()函数可以覆盖其内容(因为已知Microsoft Debug C RunTime)。

答案 1 :(得分:1)

  1. 尝试具体 - 什么不起作用?你的代码是否编译?你在运行时遇到错误吗?您没有在方案中获得预期的结果吗?

  2. 您的deleteFromList函数应该注意删除头部或尾部(即toRemove->prevtoRemove->next分别为空时。

  3. temp = lst->head;以及lst为空时会发生什么?您将收到运行时错误

  4. 如果您被删除,则不会更新headtail

  5. 这就是我第一眼看到的。

答案 2 :(得分:0)

你应该写while(temp->next)来纠正这个....你也可以简单地使用free解除分配节点。并且为了消除悬空指针问题,您应该在释放该节点后将其设为NULL