方法一: 用递归实现先序遍历的方法
由先序遍历的方式及其规律可知:先访问根节点再遍历左子树,最后访问右子树。
其规律不知道的需要翻阅一下教材,故编写代码的时候可以应用此规律。
我们需要了解什么是二叉树的前序遍历:按照访问根节点——左子树——右子树的方式遍历这棵树,而在访问左子树或者右子树的时候,我们按照同样的方式遍历,直到遍历完整棵树。因此整个遍历过程天然具有递归的性质,我们可以直接用递归函数来模拟这一过程.
定义 preorder(head) 表示当前遍历到 head节点的答案。按照定义,我们只要首先将head节点的值加入答案,然后递归调用 preorder(head.left) 来遍历head节点的左子树,最后递归调用 preorder(head.right) 来遍历 head 节点的右子树即可,递归终止的条件为碰到空节点。
复杂度分析
时间复杂度:O(n),其中 n是二叉树的节点数。每一个节点恰好被遍历一次。
空间复杂度:O(n),为递归过程中栈的开销,平均情况下为 O(logn),最坏情况下树呈现链状,为 O(n)。
代码如下
/**
* Definition for a binary tree node.
* struct TreeNode {
* int val;
* TreeNode *left;
* TreeNode *right;
* TreeNode() : val(0), left(nullptr), right(nullptr) {}
* TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}
* TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left), right(right) {}
* };
*/
class Solution {
public:
/* void inorder(TreeNode* head,vector<int>& a)
{
if(head==nullptr){
return ;
}
a.push_back(head->val);
inorder(head->left,a);
inorder(head->right,a);
}*/
void preorder(TreeNode* head,vector<int>&a){
if(head==nullptr){
return;//先访问根节点
}
a.push_back(head->val);
if(head->left){//若有左子树,则访问左子树
preorder(head->left,a);
}
if(head->right){//若有右子树,则访问右子树
preorder(head->right,a);
}
}
vector<int> preorderTraversal(TreeNode* head) {
vector<int>a;
preorder(head,a);
return a;
}
};
方法二:用栈实现(非递归方式)先序遍历
具体步骤:
栈实现非递归遍历的思路如下:
1.定义一个栈s,将根节点压入栈。
2.若栈不为空,则将栈顶压入结果数组ans,同时弹出栈顶。
3.若栈顶节点的右子树存在,则压入该节点入栈,
若栈顶节点的左子树存在,则将其压入栈,
这样做的方式是左子树在右子树的上方,待其弹出是也是先左后右。
4.重复操作,最终返回结果
复杂度分析
时间复杂度:O(n),其中 n 是二叉树的节点数。每一个节点恰好被遍历一次。
空间复杂度:O(n),为迭代过程中显式栈的开销,平均情况下为 O(logn),最坏情况下树呈现链状,为 O(n)。
/**
* Definition for a binary tree node.
* struct TreeNode {
* int val;
* TreeNode *left;
* TreeNode *right;
* TreeNode() : val(0), left(nullptr), right(nullptr) {}
* TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}
* TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left), right(right) {}
* };
*/
class Solution {
public:
/* void inorder(TreeNode* head,vector<int>& a)
{
if(head==nullptr){
return ;
}
a.push_back(head->val);
inorder(head->left,a);
inorder(head->right,a);
}*/
vector<int> preorderTraversal(TreeNode* head) {
vector<int>ans;
if(head==nullptr){
return ans;
}
stack<TreeNode*>s;
s.push(head);
while(s.size()){
auto node=s.top();
ans.push_back(node->val);
s.pop();
if(node->right){
s.push(node->right);
}
if(node->left){
s.push(node->left);
}
}
return ans;
}
};