二級指標在連結串列中的應用
阿新 • • 發佈:2021-01-28
重讀了兩本書:Stephen A.Maguire的《程式設計精粹:Microsoft編寫優質無錯C程式祕訣》和David R. Hanson的《C語言介面與實現:建立可重用軟體的技術》。兩本書都有對連結串列的操作。
假設有如圖所示的連結串列,連結串列節點的pb
成員指向一個緩衝塊,刪除節點函式根據緩衝塊的首地址,找到節點並刪除節點:
《程式設計精粹》使用一個變數pbiPrev
來儲存前一個節點位置,並且要處理刪除的是第一個節點A這種邊界條件:
void FreeBlockInfo(byte *pbToFree)
{
blockinfo *pbi, * pbiPrev;
pbiPrev = NULL;
for(pbi = pbiHead; pbi != NULL; pbi = pbi->pbiNext)
{
if(fPtrEqual(pbi->pb, pbToFree)
{
if(pbiPrev == NULL)
pbiHead = pbi->pbiHead;
else
pbiPrev->pbiNext = pbi->pbiNext;
break;
}
pbiPrev = pbi;
}
/*如果pbi是NULL, 說明引數pbToFree非法*/
ASSERT(pbi != NULL);
/*在釋放前破壞掉要釋放記憶體中的內容*/
memset(pbi, bGarbage, sizeof(blockinfo));
free(pbi);
}
《C語言介面與實現》使用了二級指標,可以很巧妙的省掉變數pbiPrev
以及邊界判斷:
void FreeBlockInfo(byte *pbToFree)
{
blockinfo **ppbi, *pbiFind;
pbiFind = NULL;
for(ppbi = &pbiHead; *ppbi != NULL; ppbi = &(*ppbi) ->pbiNext)
{
if(fPtrEqual((*ppbi)->pb, pbToFree)
{
pbiFind = *ppbi;
*ppbi = (*ppbi)->pbiNext;
break;
}
}
/*如果pbiFind是NULL, 說明引數pbToFree非法*/
ASSERT(pbiFind != NULL);
/*在釋放前破壞掉要釋放記憶體中的內容*/
memset(pbiFind, bGarbage, sizeof(blockinfo));
free(pbiFind);
}