递归方法的核心是将大问题拆解为规模更小的同类子问题,直至达到可直接求解的基准条件;该条件必须明确、可达且覆盖所有输入路径,每次递归调用须缩小问题规模,返回值需体现子问题解到原问题解的组合逻辑。

递归方法的核心不是“反复调用自己”,而是“把大问题拆成小一号的同类问题,直到小到能直接回答”。基准条件就是那个“小到能直接回答”的临界点,它不是可有可无的限制,而是整个递归逻辑成立的前提。
基准条件必须明确且可达
它要满足两个要求:一是能被真实触发(比如数组索引不会越界、数字会逐步减到 0 或 1),二是覆盖所有可能的输入路径。比如计算阶乘时写 if (n == 0 || n == 1),而不是只写 n == 0,因为传入 1 时也该立刻返回,否则还会继续调用 factorial(0),多走一层——虽不影响结果,但不严谨。
- 负数输入要提前拦截,否则 factorial(-1) 会无限调用 factorial(-2)、factorial(-3)…
- 字符串反转中,基准是 s.length() <= 1,而不是 s.length() == 0,因为单字符无需反转,直接返回最自然
- 数组求和时,基准可以是 index >= arr.length(越界即停),也可以是 index == arr.length - 1(只加最后一个),关键看递归调用时下标怎么推进
递归调用必须缩小问题规模
每次 self-call 都得让参数更接近基准条件,否则就是无效递归。这不是靠直觉,而是靠设计:你得清楚“小一号的问题”长什么样。
在 Java 中初始化和管理阿里云 SDK客户端。包括单例模式、线程安全、endpoint 与 region 配置、VPC 终端节点、同步与异步等。
- 阶乘中,n 变成 n-1,数值变小,离 0 或 1 更近
- 字符串反转中,s.substring(1) 去掉首字符,长度减 1,离长度 ≤1 更近
- 二分查找递归版,每次把搜索范围缩成一半,左右边界必然收敛
返回值要体现“子问题解如何组合成原问题解”
递归不是只靠“调用自己”就完事,关键是每层返回的结果怎么参与上层计算。这一步常被初学者忽略,导致逻辑断层。
立即学习“Java免费学习笔记(深入)”;
- factorial(n) 返回的是 n * factorial(n-1),不是单纯调用,而是把子结果乘进来
- reverseString(s) 返回的是 reverseString(s.substring(1)) + s.charAt(0),把首字符放到反转后的尾部
- 数组求和若从头开始,可写为 arr[0] + sum(arr, 1);若从尾开始,则是 sum(arr, len-1) + arr[len-1]
调试时重点观察“递”和“归”两个阶段
运行时,方法先一路向下“递”到基准条件,再逐层向上“归”并计算。可以在递归入口加打印,比如 System.out.println("进入 f(" + n + ")");,就能看清调用栈深度和参数变化路径。一旦发现某层没返回、或参数没变小,基本就是基准没设对,或递归调用写错了。

















