c技巧:用指针的指针移除单链表中元素

今天看到linus曾经提到的一个指针的指针操作单链表的技巧,挺有意思的,记录一下。


原文:


http://meta.slashdot.org/story/12/10/11/0030249/linus-torvalds-answers-your-questions


I've seen too many people whodelete a singly-linked list entry by keeping track of the "prev"entry, and then to delete the entry, doing something like

if (prev)
prev->next = entry->next;
else
list_head = entry->next;

and whenever I see code like that, I just go "This person doesn'tunderstand pointers". And it's sadly quite common.

People who understand pointers just use a "pointer to the entrypointer", and initialize that with the address of the list_head. Andthen as they traverse the list, they can remove the entry withoutusing any conditionals, by just doing a "*pp = entry->next".


即,在单链表中删除元素时,通常的做法是判断待删除元素的prev是否存在,如果存在则让该元素的prev的next指向该元素的next,如果prev不存在,则让list_head指向该元素的next:

 

Node* entry = list_head;
Node* prev = NULL;
while(entry){
    if(entry->needRemove()){  
        if(prev)
            prev->next = entry->next;
        else
            list_head = entry->next;

  
        Node *next = entry->next;  

        free(entry);
        entry = next;
    }
    else{ 
        prev = entry;
        entry = entry->next;
 }
}


linus说,这么做的人不懂指针。。。高手就是高手,霸气。

好吧,看看linus的做法:

Node** pp = &list_head;

while(*pp){
    if((*pp)->needRemove()){
        Node* entry = *pp;
        *pp = entry->next;
        free(entry);
    }
    else{
        pp = &(*pp)->next;
    }
}



用指针的指针去遍历单链表,如果不去删除元素,当然是没有必要,但是如果要删除元素,简单的一句:*pp = entry->next 就可以达到prev->next=entry->next的效果,而且不用判断prev是否存在,因为pp永远指向prev->next,当没有prev时, pp指向list_head。且不用在删除前保存prev这个指针。

不得不说,确实精妙。


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值