在Java后端与算法面试中,算法题:二叉树的中序遍历(LeetCode 94)是考察二叉树操作能力的“黄金入门题”——它不仅是二叉树遍历的核心基础,更是验证二叉搜索树、寻找第k小元素等复杂问题的前置子问题。根据鳄鱼java的面试案例库统计,90%的中大厂Java面试都会考察这道题,其中仅能写出递归解法的候选人通过率不足25%,而掌握迭代与Morris遍历的候选人通过率高达90%以上。这道题的核心价值,是通过一个简单的遍历操作,筛选出具备“递归思维+栈应用+空间优化”能力的Java开发者,而非只会背题的应试者。
一、面试题本质:从“遍历”到“二叉树核心思维考察”

很多候选人以为算法题:二叉树的中序遍历(LeetCode 94)只是要你写出遍历代码,但实际上,面试官的真实意图是考察三个核心能力:一是你能否理解二叉树的递归定义(左-根-右的遍历顺序);二是你能否用栈模拟递归过程(避免递归栈溢出);三是你能否掌握空间复杂度为O(1)的优化方法(体现底层思维深度)。
鳄鱼java的资深面试官分享:这道题的评分标准分三个层级:及格级(能写出递归解法)、良好级(能写出栈实现的迭代解法)、优秀级(能写出Morris遍历并讲清原理)。优秀级候选人往往能直接进入二面,因为他们具备Java项目中处理树形数据场景的核心思维——比如树形结构的配置解析、数据库索引树的遍历、日志树的分析等场景,都需要这道题的底层逻辑支持。
二、解法1:递归(基础入门,代码简洁)
递归解法是算法题:二叉树的中序遍历(LeetCode 94)的基础入门解法,代码简洁易懂,适合新手理解中序遍历的“左-根-右”顺序,但面试中仅写递归解法会被认为基础能力不足,仅能拿到及格分。
核心思路:根据二叉树的递归定义,先递归遍历左子树,再访问根节点,最后递归遍历右子树。终止条件是当前节点为null,直接返回。
Java代码与边界处理:
public ListinorderTraversal(TreeNode root) { List result = new ArrayList<>(); // 边界条件:空树直接返回空列表 if (root == null) return result; inorder(root, result); return result; } // 递归辅助函数 private void inorder(TreeNode node, List
result) { // 终止条件:当前节点为空 if (node == null) return; // 1. 递归遍历左子树 inorder(node.left, result); // 2. 访问当前节点(根) result.add(node.val); // 3. 递归遍历右子树 inorder(node.right, result); }
时间空间复杂度:时间O(n),每个节点被访问一次;空间O(h),h是二叉树的高度,递归栈的深度等于树的高度(最坏情况是链式树,h=n,空间O(n))。
面试得分点:是否单独写了辅助函数(避免每次创建List的开销),是否处理了空树的边界条件,这是区分“会写代码”和“写好代码”的细节。
三、解法2:迭代(栈实现,面试重点)
迭代解法(栈实现)是算法题:二叉树的中序遍历(LeetCode 94)的面试重点,能体现你对栈的理解以及对递归过程的模拟能力,是面试官期待的标准解法,也是鳄鱼java的算法训练营中重点讲解的内容。
核心思路:用栈模拟递归过程,先将所有左子树节点入栈,直到左子节点为null;然后出栈访问节点,再将右子节点入栈,重复上述过程,直到栈为空且当前节点为null。
Java代码与步骤解析:
public ListinorderTraversal(TreeNode root) { List result = new ArrayList<>(); Stack stack = new Stack<>(); TreeNode curr = root; while (curr != null || !stack.isEmpty()) { // 1. 将当前节点的所有左子节点入栈 while (curr != null) { stack.push(curr); curr = curr.left; } // 2. 出栈并访问节点(此时左子树已遍历完毕) curr = stack.pop(); result.add(curr.val); // 3. 遍历右子树 curr = curr.right; } return result;}
步骤解析:比如遍历二叉树1(null,2(3,null)),先将1、3入栈;弹出3访问,处理3的右子树(null);弹出1访问,处理1的右子树2;将2入栈,弹出2访问,处理2的右子树(null),最终得到[3,1,2]。
时间空间复杂度:时间O(n),每个节点入栈出栈各一次;空间O(h),栈的大小等于树的高度(最坏情况O(n))。
面试得分点:能否清晰讲解“左子树入栈-出栈访问-处理右子树”的循环逻辑,是否处理了“栈不为空但curr为空”的情况(比如右子树为空时仍要继续出栈),这是面试官高频追问的细节。
四、解法3:Morris遍历(进阶优化,O(1)空间)
Morris遍历是算法题:二叉树的中序遍历(LeetCode 94)的进阶优化解法,能达到O(1)的空间复杂度,是面试中展示思维深度的“加分项”,也是鳄鱼java的进阶算法课程中讲解的内容。
核心思路:利用二叉树的空闲右指针(线索二叉树思想),将左子树的最右节点的右指针指向当前节点,无需额外栈空间;遍历完成后恢复树的原始结构,避免破坏树的形态。
Java代码与线索恢复:
public ListinorderTraversal(TreeNode root) { List result = new ArrayList<>(); TreeNode curr = root; TreeNode prev = null; // 左子树的最右节点 while (curr != null) { if (curr.left == null) { // 左子树为空,直接访问当前节点,遍历右子树 result.add(curr.val); curr = curr.right; } else { // 找到左子树的最右节点 prev = curr.left; while (prev.right != null && prev.right != curr) { prev = prev.right; } if (prev.right == null) { // 线索未创建:将最右节点的右指针指向当前节点,遍历左子树 prev.right = curr; curr = curr.left; } else { // 线索已创建:恢复树结构,访问当前节点,遍历右子树 prev.right = null; result.add(curr.val); curr = curr.right; } } } return result;}
时间空间复杂度:时间O(n),每个节点最多被访问两次;空间O(1),仅使用常数级别的变量,无需栈空间。
面试得分点:能否讲清“线索创建-遍历左子树-线索恢复”的逻辑,是否强调恢复树结构的重要性(避免破坏输入树),这是区分“普通开发者”和“算法专家”的关键。
五、面试高频陷阱:90%Java开发者踩过的坑
根据鳄鱼java的面试案例统计,以下3个陷阱的错误率均超90%,是面试官最爱挖
版权声明
本文仅代表作者观点,不代表百度立场。
本文系作者授权百度百家发表,未经许可,不得转载。





