leetcode 114 二叉树转链表

给定一个二叉树,原地将它展开为链表。
例如,给定二叉树
1
/ \
2 5
/ \ \
3 4 6
将其展开为:
1
  \
  2
   \
    3
     \
      4
       \
        5
         \
          6

来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/flatten-binary-tree-to-linked-list
给定一个二叉树,将该二叉树就地转化为单链表。单链表中节点顺序为二叉树前序遍历顺序
思考:
前序遍历二叉树,将节点指针push进入vector,顺序遍历vector中的节点,链接相邻两节点,形成单链表。按顺序遍历vector,将前面的节点左指针置空,右指针与后面的节点相连,该方法虽然可以通过题目,但不满足就地转化的条件,实现代码如下:

 //单链表仍使用该数据结构,即left = NULL, right = next
class Solution {
public:
    void flatten(TreeNode* root) {
        std::vector<TreeNode *> node_vec;
        preorder(root, node_vec);
        for (int i = 1; i < node_vec.size(); i++){
            node_vec[i-1]->left = NULL;
            node_vec[i-1]->right = node_vec[i];
        }
    }
private:
    void preorder(TreeNode *node, std::vector<TreeNode *> &node_vec){
        if(!node){
            return;
        }
        node_vec.push_back(node);
        preorder(node->left, node_vec);
        preorder(node->right, node_vec);
    }
};

就地逆转二叉树转链表的代码如下:

/**
 * Definition for a binary tree node.
 * struct TreeNode {
 *     int val;
 *     TreeNode *left;
 *     TreeNode *right;
 *     TreeNode(int x) : val(x), left(NULL), right(NULL) {}
 * };
 */
 //单链表仍使用该数据结构,即left = NULL, right = next
class Solution {
public:
    void flatten(TreeNode* root) {
        TreeNode *last = NULL;   //每次递归调用后的最后一个last指针
        preorder(root, last);
    }
private:
    void preorder(TreeNode *node, TreeNode *&last){
        //node为当前的节点
        //last为当前子树的先序遍历的最后一个节点,传引用会传出
        if (!node){
            return;
        }
        if (!node->left && !node->right){   //如果是一个叶节点,无左右子树,则last为本身,直接return
            last = node;
            return;
        }
        TreeNode *left = node->left;    //备份左右指针
        TreeNode *right = node->right;
        TreeNode *left_last = NULL;     //设置左右子树最后一个节点的变量
        TreeNode *right_last = NULL;  
        if (left){
            preorder(left, left_last);   //若有左子树,递归将左子树转化单链表
            node->left = NULL;          //左指针赋空
            node->right = left;        //完成左子树对应根节点的链接
            last = left_last;          //将该节点的last保存为左子树的last
        }
        if (right){                    //若有右子树,递归将右子树转换单链表
            preorder(right, right_last);   
            if (left_last){  //若node找到左子树最后一个节点(有左子树)
                left_last->right = right;   //左子树尾巴和右子树头部的链接
            }
            last = right_last;   //传出最后一个节点的指针,给调用它递归的函数
        }
    }
};
发布了65 篇原创文章 · 获赞 4 · 访问量 997

猜你喜欢

转载自blog.csdn.net/CLZHIT/article/details/103941350
今日推荐