1. 程式人生 > 其它 >[每日一題] [力扣430] 扁平化多級雙向連結串列 2021.9.24

[每日一題] [力扣430] 扁平化多級雙向連結串列 2021.9.24

題目描述

多級雙向連結串列中,除了指向下一個節點和前一個節點指標之外,它還有一個子連結串列指標,可能指向單獨的雙向連結串列。這些子列表也可能會有一個或多個自己的子項,依此類推,生成多級資料結構,如下面的示例所示。

給你位於列表第一級的頭節點,請你扁平化列表,使所有結點出現在單級雙鏈表中。

示例 1:

輸入:head = [1,2,3,4,5,6,null,null,null,7,8,9,10,null,null,11,12]
輸出:[1,2,3,7,8,11,12,9,10,4,5,6]
解釋:

輸入的多級列表如下圖所示:

扁平化的連結串列如下圖

來源:力扣(LeetCode)
連結:

https://leetcode-cn.com/problems/flatten-a-multilevel-doubly-linked-list
著作權歸領釦網路所有。商業轉載請聯絡官方授權,非商業轉載請註明出處。

思路

dfs 把child儲存在stack中,如果遍歷完child的連結串列到空。再把stack彈棧把child的連結串列尾續到原來壓棧的地方。

如圖

程式碼

/*
// Definition for a Node.
class Node {
public:
    int val;
    Node* prev;
    Node* next;
    Node* child;
};
*/

class Solution {
public:
    Node* flatten(Node* head) {
        auto root = head;
        std::stack<Node *> stack;
        do {
            // while head 之後一定可以找到這一層的最後的節點。
            Node *head_previous = head;
            //printf("Go Down Through !\n");
            while (head) {
                head_previous = head;
                if (head->child) {
                    // stack中儲存head的指標
                    stack.push(head);
                    //printf("Push Head -> %d\n",head->val);
                    head = head->child;
                    continue;
                }
                //printf("Go Next Head -> %d\n",head->val);
                head = head->next;
            }
            if(!stack.empty()) {
                // 獲取棧頂的head元素
                Node* top = stack.top();
                // 彈出
                stack.pop();
                // 把child置空 並把子結點保留
                Node* head_child = top->child;
                top->child = nullptr;

                Node* head_next = top->next;

                // 節點12的next置為9
                head_previous->next = head_next;
                if(head_next) {
                    //9的prev置為12
                    head_next->prev = head_previous;
                }

                // head->next = child;
                top->next = head_child;
                if(head_child) {
                    head_child->prev = top;
                }
                head = head_previous;
            }
        } while (!stack.empty() || head);
        return root;
    }
};