1. 程式人生 > >劍指Offer(二十五):復雜鏈表的復制

劍指Offer(二十五):復雜鏈表的復制

span page div 完成 oop conn 結果 新的 復雜鏈表

技術分享圖片

一、前言

本系列文章為《劍指Offer》刷題筆記。

刷題平臺:牛客網

書籍下載:共享資源

二、題目

輸入一個復雜鏈表(每個節點中有節點值,以及兩個指針,一個指向下一個節點,另一個特殊指針指向任意一個節點),返回結果為復制後復雜鏈表的head。(註意,輸出結果中請不要返回參數中的節點引用,否則判題程序會直接返回空)

1、思路

大部分人首先想到的可能是先復制復雜指針的label和next,然後再查找random並更新。查找random又分為兩種,一種是每次都從頭查找,時間復雜度為O(n^2);另一種是空間換時間,復制label和next的同時建立一個hash表來存放新舊復雜指針的對應關系,所以後續只需一步就能找到random,算法時間復雜度為O(n)。

我們這裏將復雜鏈表的復制過程分解為三個步驟。在寫代碼的時候我們每一步定義一個函數,這樣每個函數完成一個功能,整個過程的邏輯也就非常清晰明了了。

我們這裏采用三步:

  • 第一步:復制復雜指針的label和next。但是這次我們把復制的結點跟在元結點後面,而不是直接創建新的鏈表;
  • 第二步:設置復制出來的結點的random。因為新舊結點是前後對應關系,所以也是一步就能找到random;
  • 第三步:拆分鏈表。奇數是原鏈表,偶數是復制的鏈表。

有圖思路更清晰:

技術分享圖片技術分享圖片

技術分享圖片

技術分享圖片

C++:

/*
struct RandomListNode {
    int label;
    struct RandomListNode *next, *random;
    RandomListNode(int x) :
            label(x), next(NULL), random(NULL) {
    }
};
*/ class Solution { public: //第一步,復制復雜指針的label和next void CloneNodes(RandomListNode* pHead){ RandomListNode* pNode = pHead; while(pNode != NULL){ RandomListNode* pCloned = new RandomListNode(0); pCloned->label = pNode->label; pCloned
->next = pNode->next; pCloned->random = NULL; pNode->next = pCloned; pNode = pCloned->next; } } //第二步,處理復雜指針的random void ConnectSiblingNodes(RandomListNode* pHead){ RandomListNode* pNode = pHead; while(pNode != NULL){ RandomListNode* pCloned = pNode->next; if(pNode->random != NULL){ pCloned->random = pNode->random->next; } pNode = pCloned->next; } } //第三步,拆分復雜指針 RandomListNode* ReconnectNodes(RandomListNode* pHead){ RandomListNode* pNode = pHead; RandomListNode* pClonedHead = NULL; RandomListNode* pClonedNode = NULL; if(pNode != NULL){ pClonedHead = pClonedNode = pNode->next; pNode->next = pClonedNode->next; pNode = pNode->next; } while(pNode != NULL){ pClonedNode->next = pNode->next; pClonedNode = pClonedNode->next; pNode->next = pClonedNode->next; pNode = pNode->next; } return pClonedHead; } RandomListNode* Clone(RandomListNode* pHead) { CloneNodes(pHead); ConnectSiblingNodes(pHead); return ReconnectNodes(pHead); } };

劍指Offer(二十五):復雜鏈表的復制