Flatten Binary Tree to Linked List (LeetCode #114 Medium)(LintCode #453 Easy)
114. Flatten Binary Tree to Linked List (Medium)
453. Flatten Binary Tree to Linked List (Easy)
解法1: 用stack.
class Solution {
public:
void flatten(TreeNode *root) {
if(!root) return;
TreeNode *pnode = NULL;
stack<TreeNode*> s;
s.push(root);
while(!s.empty()){
root = s.top(); s.pop();
if(pnode){
pnode->left = NULL;
pnode->right = root;
}
if(root->right) s.push(root->right);
if(root->left) s.push(root->left);
pnode = root;
}
pnode->left = pnode->right = NULL;
}
};
解法2: 递归
class Solution {
private:
void _flatten(TreeNode *root, TreeNode **ph, TreeNode **pt) {
if (!root) {
*ph = *pt = NULL;
return;
}
TreeNode *h1, *t1, *h2, *t2;
_flatten(root->left, &h1, &t1);
_flatten(root->right, &h2, &t2);
root->left = NULL;
*ph = *pt = root;
if (h1) {
root->right = h1;
*pt = t1;
if (h2) {
t1->right = h2;
*pt = t2;
}
} else if (h2) {
root->right = h2;
*pt = t2;
}
}
public:
void flatten(TreeNode *root) {
TreeNode *h, *t;
_flatten(root, &h, &t);
}
};
ph
其实一定指向root
, 所以可以省略. 简化为一下代码:
class Solution {
private:
void _flatten(TreeNode *root, TreeNode **ptail) {
if (!root) {
*ptail = NULL;
return;
}
TreeNode *t1, *t2;
_flatten(root->left, &t1);
_flatten(root->right, &t2);
if (t1) {
t1->right = root->right;
root->right = root->left;
root->left = NULL;
}
*ptail = t2 ? t2 : (t1 ? t1 : root);
}
public:
void flatten(TreeNode *root) {
TreeNode *t;
_flatten(root, &t);
}
};
解法3: @Netario36
假设flatten
函数已经可以以前序遍历完成flatten的任务, 且flatten(root->left)
和flatten(root->right)
已完成, 那么接下来要做的操作就是:
记flatten(root->left)
后该链表的最后一个节点是tail
.
那么
tail->right = root->right;
root->right = tail;
root->left = NULL;
就可以把root
节点, root->left
的flatten子树, 和root->right
的flatten子树串起来.
这代码看起来简洁, 但是把左子树处理完并插入到root
和root->right
之间后, 要处理插入前的root->right
子树需要递归N
次, 其中N
是root->left
子树节点数. 也就是说, 有很多不必要的递归.
//@Netario36
class Solution {
private:
TreeNode *tail;
public:
void flatten(TreeNode *root) {
if (!root) return;
if (root->left) {
flatten(root->left);
tail->right = root->right;
root->right = root->left;
root->left = NULL;
}
tail = root;
flatten(root->right);
}
};
基于@Netario36
的版本我写了一个前序遍历结构更明显, 没有无用的递归的版本.
class Solution {
private:
TreeNode *tail;
public:
void flatten(TreeNode *root) {
if (!root) return;
tail = root;
if (root->left) {
flatten(root->left);
tail->right = root->right;
root->right = root->left;
root->left = NULL;
}
flatten(tail->right);
}
};
解法4: @versavitality
参数rightRoot
是root
的右兄弟节点, 返回值为root
子树与rightRoot
子树flatten之后的根节点.
TreeNode *right = _flatten(root->right, rightRoot);
将root->right
子树与rightRoot
子树flatten到一起.
root->right = _flatten(root->left, right);
将root->left
子树与上一步的结果flatten到一起.
// @versavitality
class Solution {
private:
TreeNode* _flatten(TreeNode *root, TreeNode *rightRoot) {
if (!root) return rightRoot;
TreeNode *right = _flatten(root->right, rightRoot);
root->right = _flatten(root->left, right);
root->left = NULL;
return root;
}
public:
void flatten(TreeNode *root) {
_flatten(root, NULL);
}
};
蛋疼的博客园, 有@
字符会翻译成mailto链接...又不知道怎么取消, 只能用``包起来了.
最新文章
- 30分钟带你快速入门MySQL教程
- 【STL】重载运算符
- [3D跑酷] GUIManager UI管理
- 学习KMP算法
- QT 的信号与槽机制介绍
- C语言文件操作解析(五)之EOF解析(转载)
- Mysql联合查询UNION和UNION ALL的使用介绍
- .htaccess Rewrite apache重写和配置
- CSharp设计模式读书笔记(9):组合模式(学习难度:★★★☆☆,使用频率:★★★★☆)
- javascript ajax 脚本跨域调用全解析
- BOGEER博格尔YT-813码表使用说明书 (我的是YT-823)
- 数位dp——hud3652
- c++11线程池
- PHP设计模式注意点
- Python类的构成元素
- mongodb初始化并使用node.js实现mongodb操作封装
- 采用jquery同django实现ajax通信
- UITableView _endCellAnimationsWithContext崩溃
- Android 使用zxing生成二维码的方法
- C#编译和运行原理
热门文章
- postgresql 字符串拼接";||“的使用
- C#做的一个加密/解密的类
- C#微信公众号开发 -- (一)开发之前的准备
- WildFly 9.0.2+mod_cluster-1.3.1 集群配置
- 学习笔记_Java_day13_JSTL标签库(1、2、3、4、5、6、7、8)
- ios专题 -KVO , KVC
- VMware Workstation不能启用虚拟设备floppy0由于灭有相应的有效设备在主机上. 你要尝试在每次打开虚拟机电源时连接此虚拟设备?
- 我爆一个托 QQ305242038 电话 18782169971
- mysql学习笔记2
- [翻译]ASP.NET Web API 2入门