二叉树——二叉树的直径

题目:
给你一棵二叉树的根节点,返回该树的 直径 。
二叉树的 直径 是指树中任意两个节点之间最长路径的 长度 。这条路径可能经过也可能不经过根节点 root 。
两节点之间路径的 长度 由它们之间边数表示。

核心思路:

  1. 二叉树直径定义:任意两节点间最长路径的边数,路径可能不经过根节点。
  2. 关键转化
  • 一个节点的**左子树高度+右子树高度 **= 以该节点为中心的路径长度
  • 整棵树的直径 = 所有节点[左高+右高]的最大值
  1. 递归方案:
  • 后序遍历递归计算每个节点的左右子树高度
  • 遍历过程中实时更新最大直径
  • 最终返回最大直径

完整代码实现如下:

// 二叉树节点定义
class TreeNode {

int val;
TreeNode left;
TreeNode right;
TreeNode() {}
TreeNode(int val) { this.val = val; }
TreeNode(int val, TreeNode left, TreeNode right) {
this.val = val;
this.left = left;
this.right = right;
}
}

class Solution {

// 全局变量,记录最大直径
int maxDiameter = 0;

public int diameterOfBinaryTree(TreeNode root) {
// 递归计算高度,同时更新最大直径
height(root);
return maxDiameter;
}

// 递归计算节点高度:高度 = 左右子树最大高度 + 1
private int height(TreeNode node) {
// 空节点高度为0
if (node == null) {
return 0;
}

// 递归计算左、右子树高度
int leftHeight = height(node.left);
int rightHeight = height(node.right);

// 更新最大直径:当前节点的路径长度 = 左高 + 右高
maxDiameter = Math.max(maxDiameter, leftHeight + rightHeight);

// 返回当前节点的高度(供父节点使用)
return Math.max(leftHeight, rightHeight) + 1;
}
}

代码解释:

  1. TreeNode 类:标准二叉树节点结构,包含值、左孩子、右孩子。
  2. maxDiameter:全局变量,实时记录遍历过程中找到的最长路径。
  3. diameterOfBinaryTree 方法:主方法,调用递归函数后返回结果。
  4. height 递归方法
  • 终止条件:空节点返回高度 0
  • 递归计算左右子树高度
  • 用左高+右高更新最大直径
  • 返回当前节点的高度(用于上层递归计算)

复杂度分析

  • 时间复杂度:O (n) —— 每个节点仅遍历一次
  • 空间复杂度:O (h) —— h 为树的高度,递归调用栈的深度

特别注意一点

递归的返回值是当前节点的高度,并不是我们所要的路径长度,而是用于上层递归计算最大直径所需要的左右子树高度和,因此在主函数中,我们只是调用了递归height(root),而没有接收其返回值,而是返回递归调用中实时记录的最大路径长度(maxDiameter)

  • 递归返回高度时必须+1(因为高度时顶点数)
  • 计算直径时不加1
  • 高度:算的是顶点数(所以要+1)
  • 直径:直接用左右高度相加,就是边数(不用+1)

总结:

  1. 二叉树直径 = 所有节点的左子树高度 + 右子树高度的最大值
  2. 后序递归一次遍历完成「高度计算」和「直径更新」
  3. 时间复杂度最优 O (n),代码简洁高效
posted @ 2026-04-14 15:33  ZealousMclaren  阅读(17)  评论(0)    收藏  举报