二叉树的前序遍历(leetcode144)
因为题目中要求的是返回节点值的前序遍历,因此我们将集合的泛型定义为Integer即可
思路分析(递归实现)
1:前序遍历的顺序是根--->左--->右--->由于题目中给定了二叉树的根结点root,因此先判断根节点是否为空
2:观察题目,由于题目要求返回的是一个List集合,所以要定义一个集合ArrayList,定义一个递归的方法,
3:根节点不为空时,遍历二叉树,输入当前根节点的值,并将值保存到集合list中,然后递归的向左调用,再递归的向右调用
class Solution {
public List<Integer> preorderTraversal(TreeNode root) {
//递归前序遍历
//定义一个集合
List<Integer> list=new ArrayList<>();
method(list,root);
return list;
}
public void method(List<Integer> list,TreeNode root){
if(root==null){
return;
}
list.add(root.val);
method(list,root.left);
method(list,root.right);
}
}
class Solution {
public List<Integer> preorderTraversal(TreeNode root) {
//递归中序遍历
List<Integer> list=new ArrayList<>();
method(list,root);
return list;
}
public void method(List<Integer> list,TreeNode root){
if(root==null){
return;
}
method(list,root.left);
list.add(root.val);
method(list,root.right);
}
}
class Solution {
public List<Integer> preorderTraversal(TreeNode root) {
//递归后序遍历
List<Integer> list=new ArrayList<>();
method(list,root);
return list;
}
public void method(List<Integer> list,TreeNode root){
if(root==null){
return;
}
method(list,root.left);
method(list,root.right);
list.add(root.val);
}
}
思路分析(栈实现中序遍历)
1:利用栈先进后出的原则,定义一个栈Stack和一个集合ArrayList
2:(当前根节点不为空时)先向左子树遍历,每遍历一个节点,就将该节点入栈,当遍历到左子树的最后一个叶子结点时,出栈,用root接收,并将节点信息保存到集合list中,并将root节点香油移动
3:(当前根节点不为空并且栈不为空时)循环上述操作
class Solution {
public List<Integer> inorderTraversal(TreeNode root) {
List<Integer> list=new ArrayList<>();
Stack<TreeNode> stack=new Stack<>();
TreeNode temp=root;
while(temp!=null || !stack.isEmpty()){
while(temp!=null){
stack.push(temp);
temp=temp.left;
}
temp=stack.pop();
list.add(temp.val);
temp=temp.right;
}
return list;
}
}
思路分析(栈实现前序遍历)
与中序遍历基本类似,(当根节点不为空时)遍历节点,每遍历一个节点,就入栈,并将该节点存入集合中。当退出循序时,将节点出栈,用根节点root接收,并将根节点右移
class Solution {
public List<Integer> preorderTraversal(TreeNode root) {
List<Integer> list=new ArrayList<>();
Stack<TreeNode> stack=new Stack<>();
while(root!=null || !stack.isEmpty()){
while(root!=null){
list.add(root.val);
stack.push(root);
root=root.left;
}
root=stack.pop();
root=root.right;
}
return list;
}
}
思路分析(栈实现后序遍历)
后序遍历相较于前两种遍历来说更加复杂,因为后序遍历输出的是左子树--->右子树--->根节点
因为二叉树中左子树不能直接指向右子树,所以想先输入右子树再出根节点会比较复杂
因此,我们定义一个新节点preNode,用于保存
(根节点不为空时)向左子树遍历链表,每遍历一个节点就将该节点入栈,节点左移。
将栈顶元素出栈,用root接收,如果根节点的右子节点为空或者新节点preNode遍历过了。即新节点等于根节点的右子节点,此时将根节点的值存入集合中,新节点preNode指向当前根节点,根节点重新置空,否则节点入栈并将右移
class Solution {
public List<Integer> postorderTraversal(TreeNode root) {
List<Integer> list=new ArrayList<>();
Stack<TreeNode> stack=new Stack<>();
while(root!=null || !stack.isEmpty()){
while(root!=null){
stack.push(root);
root=root.left;
}
TreeNode preNode=null;
root=stack.pop();
if(root.right==null||root.right==preNode){
list.add(root.val);
preNode=root;
root=null;
}else{
stack.push(root);
root=root.right;
}
}
return list;
}
}