📅  最后修改于: 2023-12-03 15:21:40.359000             🧑  作者: Mango
二叉树的边界遍历是指输出一棵二叉树的所有边界节点,分为左子树的左边界节点、右子树的右边界节点和树的叶子节点。边界节点的定义是:根节点、左子树的最左边节点、右子树的最右边节点和叶子节点。
以下是二叉树节点的定义:
public class TreeNode {
int val;
TreeNode left;
TreeNode right;
TreeNode(int val) {
this.val = val;
}
}
以下是二叉树的边界遍历代码实现:
public class BoundaryTraversal {
public List<Integer> boundaryOfBinaryTree(TreeNode root) {
List<Integer> res = new ArrayList<>();
if (root != null) {
res.add(root.val); // 添加根节点
getLeftBoundary(root.left, res); // 添加左子树的左边界节点
getLeaves(root.left, res); // 添加左子树的叶子节点
getLeaves(root.right, res); // 添加右子树的叶子节点
getRightBoundary(root.right, res); // 添加右子树的右边界节点
}
return res;
}
private void getLeftBoundary(TreeNode node, List<Integer> res) {
if (node == null || (node.left == null && node.right == null)) { // 如果节点是叶子节点或为空,则返回
return;
}
res.add(node.val);
if (node.left == null) { // 如果左子树为空,则遍历右子树
getLeftBoundary(node.right, res);
} else { // 否则遍历左子树
getLeftBoundary(node.left, res);
}
}
private void getRightBoundary(TreeNode node, List<Integer> res) {
if (node == null || (node.left == null && node.right == null)) { // 如果节点是叶子节点或为空,则返回
return;
}
if (node.right == null) { // 如果右子树为空,则遍历左子树
getRightBoundary(node.left, res);
} else { // 否则遍历右子树
getRightBoundary(node.right, res);
}
res.add(node.val);
}
private void getLeaves(TreeNode node, List<Integer> res) {
if (node == null) {
return;
}
if (node.left == null && node.right == null) {
res.add(node.val);
return;
}
getLeaves(node.left, res);
getLeaves(node.right, res);
}
}
该算法采用递归的方式实现,时间复杂度为 $O(n)$,空间复杂度为 $O(n)$,其中 $n$ 是二叉树的节点个数。
二叉树的边界遍历是一道比较有意思的算法题目,相对于普通的二叉树遍历,它更加考察程序员对于二叉树边界节点的定义和理解。在实现该算法时,需要熟练掌握二叉树的遍历方式和递归思想,在代码实现时需要注意处理特殊情况,如空节点和叶子节点。