本例使用Java语言来编写无递归的二叉树中序遍历
实现方式:使用Stack保存父节点,使用一个HashSet来标记遍历过的节点,防止在遍历左子树时重复遍历。
树的节点
public class TreeNode {
int val;
TreeNode left;
TreeNode right;
TreeNode(int x){ val = x; }
}
包含中序遍历方法的类
import java.util.HashSet;
import java.util.Set;
import java.util.Stack;
public class RangeSumBST {
public static TreeNode tree;
public static void print(){
// 使用栈来保存父节点
Set<TreeNode> set = new HashSet<>();
Stack<TreeNode> stack = new Stack();
// 防止root被改变
TreeNode currNode = tree;
stack.push(currNode);
// 只要栈中还有节点就说明还有元素未被遍历
while (!stack.isEmpty() && currNode != null){
// 先遍历当前节点到最左的叶节点,遇到曾经遍历过的节点时也终止遍历
if (currNode.left != null){
while (currNode.left != null && !set.contains(currNode.left)){
stack.push(currNode.left);
currNode = currNode.left;
}
}
// 输出当前节点的值,该节点的左叶节点已经遍历完成了
currNode = stack.pop();
System.out.print(currNode.val + " ");
//已经被输出(取值)过的节点添加进HashSet中,以便不被重复遍历
set.add(currNode);
// 如果当前节点有右节点,当前节点跳到前节点的右节点上
if(currNode.right != null){
stack.push(currNode.right);
currNode = currNode.right;
}
}
}
}
测试类及输出
import org.junit.Before;
import org.junit.Test;
public class RangeSumBSTTest {
@Before
public void init(){
RangeSumBST.tree = new TreeNode(10);
RangeSumBST.tree.left = new TreeNode(5);
RangeSumBST.tree.right = new TreeNode(15);
RangeSumBST.tree.left.left = new TreeNode(3);
RangeSumBST.tree.left.left.left = new TreeNode(1);
RangeSumBST.tree.left.left.left.left = new TreeNode(0);
RangeSumBST.tree.left.right = new TreeNode(7);
RangeSumBST.tree.left.right.right = new TreeNode(8);
RangeSumBST.tree.right.right = new TreeNode(18);
}
@Test
public void fun(){
RangeSumBST.print();
}
}
Output: 0 1 3 5 7 8 10 15 18