[LeetCode] 117. Populating Next Right Pointers in Each Node II

Populating Next Right Pointers in Each Node II

Given a binary tree

struct TreeLinkNode {
TreeLinkNode *left;
TreeLinkNode *right;
TreeLinkNode *next;
}

Populate each next pointer to point to its next right node. If there is no next right node, the next pointer should be set to NULL.
Initially, all next pointers are set to NULL.
Note:
You may only use constant extra space.
Recursive approach is fine, implicit stack space does not count as extra space for this problem.
Example:
Given the following binary tree,
这里写图片描述

解析

类似于[LeetCode] 116. Populating Next Right Pointers in Each Node,只是现在不能保证二叉树是满二叉树。

解法1:队列

这个解法跟[LeetCode] 116. Populating Next Right Pointers in Each Node里的队列解法完全一样。

class Solution {
public:
    void connect(TreeLinkNode *root) {
        if (!root) return;
        queue<TreeLinkNode* > q;
        q.push(root);
        while(!q.empty()){
            int size = q.size();
            for(int i=0; i<size; i++){
                TreeLinkNode* node = q.front();
                q.pop();
                if(i< size-1)
                    node->next = q.front();
                if(node->left) q.push(node->left);
                if(node->right) q.push(node->right);
            }
        }
    }
};

解法2:递归

先找到同一层root的next节点,利用next进行依次寻找left和right,找到root的子节点next应该链接的节点,重点是先递归右子树,后递归左子树

class Solution {
public:
    void connect(TreeLinkNode *root) {
        if (!root) return;
        TreeLinkNode* cur = root->next;
        while(cur){
            if(cur->left){
                cur = cur->left;
                break;
            }
            if(cur->right){
                cur = cur->right;
                break;
            }
            cur = cur->next;
        }
        if(root->right) root->right->next = cur;
        if(root->left) root->left->next = root->right ? root->right : cur;
        connect(root->right);
        connect(root->left);
    }
};

解法3:构建函数

构建一个寻找下一层first节点的函数

    void connect(TreeLinkNode * root){
        if(!root) return;
        TreeLinkNode* cur;
        while(root){
            cur = root;
            while(cur){
                if(cur->left && cur->right){
                    cur->left->next = cur->right;
                    cur->right->next = getnextlevelFirst(cur->next);
                }
                else if(cur->left || cur->right){
                    getnextlevelFirst(cur)->next = getnextlevelFirst(cur->next);
                }
                cur = cur->next;
            }
            root = getnextlevelFirst(root);
        }
    }

    TreeLinkNode* getnextlevelFirst(TreeLinkNode* root){  //构建一个寻找下一层第一个节点的函数。
        if(!root) return NULL;
        else if(root->left) return root->left;
        else if(root->right) return root->right;
        else return getnextlevelFirst(root->next);
    }

解法4:空间复杂度O(1)

建立一个dummy结点来指向每层的首结点的前一个结点,然后指针t用来遍历这一层,我们实际上是遍历一层,然后连下一层的next,首先从根结点开始,如果左子结点存在,那么t的next连上左子结点,然后t指向其next指针;如果root的右子结点存在,那么t的next连上右子结点,然后t指向其next指针。此时root的左右子结点都连上了,此时root向右平移一位,指向其next指针,如果此时root不存在了,说明当前层已经遍历完了,我们重置t为dummy结点,root此时为dummy->next,即下一层的首结点,然后dummy的next指针清空。

class Solution {
public: 
    void connect(TreeLinkNode *root) {
        if (!root) return;
        TreeLinkNode* dummy = new TreeLinkNode(0);
        TreeLinkNode* t = dummy;
        while(root){
            if(root->left){
                t->next = root->left;
                t = t->next;
            }
            if(root->right){
                t->next = root->right;
                t = t->next;
            }
            root = root->next;
            if(!root){
                t = dummy;
                root = dummy->next;
                dummy->next = NULL;
            }
        }
    }
};

参考

http://www.cnblogs.com/grandyang/p/4290148.html

猜你喜欢

转载自blog.csdn.net/Peng_maple/article/details/82292010