Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[剑指 Offer] 36. 二叉搜索树与双向链表 #67

Open
frdmu opened this issue Aug 3, 2021 · 0 comments
Open

[剑指 Offer] 36. 二叉搜索树与双向链表 #67

frdmu opened this issue Aug 3, 2021 · 0 comments

Comments

@frdmu
Copy link
Owner

frdmu commented Aug 3, 2021

输入一棵二叉搜索树,将该二叉搜索树转换成一个排序的循环双向链表。要求不能创建任何新的节点,只能调整树中节点指针的指向。

 

为了让您更好地理解问题,以下面的二叉搜索树为例:
bstdlloriginalbst
我们希望将这个二叉搜索树转化为双向循环链表。链表中的每个节点都有一个前驱和后继指针。对于双向循环链表,第一个节点的前驱是最后一个节点,最后一个节点的后继是第一个节点。

下图展示了上面的二叉搜索树转化成的链表。“head” 表示指向链表中有最小元素的节点。
bstdllreturndll
特别地,我们希望可以就地完成转换操作。当转化完成以后,树中节点的左指针需要指向前驱,树中节点的右指针需要指向后继。还需要返回链表中的第一个节点的指针。

 

解法一:
中序遍历,保存指针,再建立链表。好理解。代码如下:

/*
// Definition for a Node.
class Node {
public:
    int val;
    Node* left;
    Node* right;

    Node() {}

    Node(int _val) {
        val = _val;
        left = NULL;
        right = NULL;
    }

    Node(int _val, Node* _left, Node* _right) {
        val = _val;
        left = _left;
        right = _right;
    }
};
*/
class Solution {
public:
    void inOrder(Node* root, vector<Node*>& vec) {
        if (!root) return;

        inOrder(root->left, vec);
        vec.push_back(root);
        inOrder(root->right, vec);
    }
    Node* treeToDoublyList(Node* root) {
        if (!root) return NULL;
        vector<Node*> vec;
        
        inOrder(root, vec);
        int n = vec.size();

        for (int i = 0; i < n-1; i++) {
            vec[i]->right = vec[i+1];
            vec[i+1]->left = vec[i];
        }
        vec[n-1]->right = vec[0];
        vec[0]->left = vec[n-1];

        return vec[0];
    }
};

解法二:
递归写法。代码如下:

class Solution {
public:
    Node *pre = NULL, *head = NULL;
    void inOrder(Node* root) {
        if (!root) return;

        inOrder(root->left);
        if (!pre) {
            head = root;        
        } else {
            pre->right = root;
            root->left = pre;

        }    
        pre = root;
        inOrder(root->right);
    } 
    Node* treeToDoublyList(Node* root) {
        if (!root) return root; 
        
        inOrder(root);             
        head->left = pre;
        pre->right = head; 
        
        return head;
    }
};
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant