Given a binary tree, return the inorder traversal of its nodes' values.

For example:
Given binary tree{1,#,2,3},

   1
\
2
/
3

return[1,3,2].

Note: Recursive solution is trivial, could you do it iteratively?

confused what"{1,#,2,3}"means? > read more on how binary tree is serialized on OJ.

OJ's Binary Tree Serialization:

The serialization of a binary tree follows a level order traversal, where '#' signifies a path terminator where no node exists below.

Here's an example:

   1
/ \
2 3
/
4
\
5

The above binary tree is serialized as"{1,2,3,#,#,4,#,#,5}".

 
方法一:利用栈
二叉树的中序遍历的整体遍历顺序:左子树->根节点->右子树,局部的遍历顺序是:左孩子->根节点->右孩子。思路:因为要先访问最左端的左孩子,故,算法的流程应是先将root的左孩子不停的压入栈中直到最后,然后访问节点的值,再转向其右孩子重复上述过程。若是root=NULL,则,不会进行while循环,直接返回res;while条件中的root是因为,遍历到根节点时,此时栈为空,而root为根节点的右孩子,即开始遍历其右子树,为循环的继续,所以加入root不为NULL的条件。代码如下:
 
/**
* Definition for binary tree
* struct TreeNode {
* int val;
* TreeNode *left;
* TreeNode *right;
* TreeNode(int x) : val(x), left(NULL), right(NULL) {}
* };
*/
class Solution {
public:
vector<int> inorderTraversal(TreeNode *root)
{
vector<int> res;
stack<TreeNode *> stk; while(root|| !stk.empty())
{
if(root) //将左孩子不停地压入栈
{
stk.push(root);
root=root->left;
}
else //到最后先访问节点本身,然后转向其右孩子
{
root=stk.top();
res.push_back(root->val);
stk.pop();
root=root->right;
}
}
return res;
}
};
方法二:递归
/**
* Definition for binary tree
* struct TreeNode {
* int val;
* TreeNode *left;
* TreeNode *right;
* TreeNode(int x) : val(x), left(NULL), right(NULL) {}
* };
*/
class Solution {
public:
vector<int> inorderTraversal(TreeNode *root)
{
vector<int> res;
inorderTrav(root,res);
return res;
}
void inorderTrav(TreeNode *root,vector<int> &res)
{
if(root==NULL) return;
inorderTrav(root->left,res);
res.push_back(root->val);
inorderTrav(root->right,res);
}
};
 
方法三:空间复杂度为O(1)

步骤:

1. 如果当前节点的左孩子为空,则输出当前节点并将其右孩子作为当前节点。

2. 如果当前节点的左孩子不为空,在当前节点的左子树中找到当前节点在中序遍历下的前驱节点。

a) 如果前驱节点的右孩子为空,将它的右孩子设置为当前节点。当前节点更新为当前节点的左孩子。

b) 如果前驱节点的右孩子为当前节点,将它的右孩子重新设为空(恢复树的形状)。输出当前节点。当前节点更新为当前节点的右孩子。

3. 重复以上1、2直到当前节点为空。

具体分析过程见AnnieKim的博客

class Solution
{
public:
vector<int> inorderTraversal(TreeNode* root)
{
vector<int> vec; TreeNode* prev=NULL;
while(root !=NULL)
{
if(root->left==NULL)
{
vec.push_back(root->val);
root=root->right;
}
else
{
prev=root->left;
while(prev->right !=NULL&&prev->right !=cur)
{
prev=prev->right;
} //关键在于前节点右孩子不存在时的处理和root节点的回溯
if(prev->right==NULL)
{
prev->right=root;
root=root->left;
}
else
{
prev->right=NULL;
vec.push_back(root->val);
root=root->right;
}
}
}
return vec;
}
};
 
 
 

最新文章

  1. WPF的学习笔记(1) -- (积累自2016年5月1日 至 2016年6月1日)
  2. 使用sql更改表的列的数据类型和添加新列和约束
  3. JVM常量池
  4. svg可缩放矢量图形
  5. 如果我用C#来输出99表
  6. html5视频播放器
  7. xml中使用foreach遍历对象
  8. www.nygwkt.com
  9. 1021 Fibonacci Again (hdoj)
  10. 单实例支撑每天上亿个请求的SSDB
  11. Linux企业运维人员必备150个命令汇总
  12. shell 脚本中执行SQL语句 -e &quot;...&quot;
  13. RxPermissions Usage
  14. linux删除历史操作命令
  15. MapWinGIS------引发类型为“System.Windows.Forms.AxHost+InvalidActiveXStateException”的异常
  16. Unity中的文件
  17. 设计模式学习--装饰者模式(Decorator Pattern)
  18. mybatis的xml配置中if text判断不为0
  19. Android应用程序的基本组件介绍
  20. UVaLive 4043 Ants (最佳完美匹配)

热门文章

  1. memory引擎和innodb引擎速度对比
  2. 「日常训练」Caterpillar(POJ-3310)
  3. 180609-Spring之事件驱动机制的简单使用
  4. Monkey用真机做测试的步骤
  5. hibernate.hbm2ddl.auto=update不能自动生成表结构
  6. CF245H Queries for Number of Palindromes
  7. TW实习日记:第27天
  8. struts2源码分析-初始化流程
  9. Python入门(5)
  10. 有个AI陪你一起写代码,是种怎样的体验?| 附ICLR论文