💡【算法题解析】爬梯子最少添加的台阶数(Leetcode风格)
🧩 题目描述
给定一个 严格递增的整数数组rungs
,数组表示梯子每个台阶的高度,你目前站在地面(高度为 0),目标是爬到最后一个台阶。
每次你最多可以爬 dist
的高度。如果某两个台阶之间高度差大于 dist
,你就无法直接跳过去。幸运的是,你可以在任意整数高度处添加新台阶,前提是添加的台阶数越少越好。
📥 输入:
rungs
: 一个严格递增的整数数组,长度为n
,表示原有台阶的位置。dist
: 一个正整数,表示你一次最多可以向上爬的高度。
📤 输出:
返回你必须添加的最少台阶数,以保证能从地面顺利爬到最后一个台阶。
✅ 示例 1:
输入:rungs = [1,3,5,10], dist = 2
输出:2
解释:
- 从地面到 1,OK;
- 1 -> 3 -> 5,OK;
- 5 -> 10,高度差为 5,需要在 7 和 9 添加两个新台阶。
✅ 示例 2:
输入:rungs = [3,6,8,10], dist = 3
输出:0
解释:每一段高度差都在3以内,不需要添加台阶。
✅ 示例 3:
输入:rungs = [3,4,6,7], dist = 2
输出:1
解释:地面到 3 高度差为 3,超出距离限制,需在高度 1 添加台阶。
✅ 示例 4:
输入:rungs = [5], dist = 10
输出:0
解释:地面到 5,距离小于等于10,直接跳上去。
🧠 解题分析
我们从地面(高度为 0)出发,逐步遍历每个台阶,检查前后两个台阶(或地面和第一个台阶)之间的高度差 diff
:
- 如果
diff ≤ dist
:不需要做任何处理; - 如果
diff > dist
:需要在这段距离之间添加一些台阶,使得任意连续台阶间的高度差 ≤dist
。
📌 如何计算需要添加几个台阶?
如果两个台阶之间的距离是 diff
,你每次最多跳 dist
,那么你最多跳的段数是 ⌈diff / dist⌉
,但是我们已经有了起点,所以我们只需添加 **⌊(diff - 1) / dist⌋**
个台阶。
🛠 解题方法(Python 实现)
class Solution:
def addRungs(self, rungs: List[int], dist: int) -> int:
prev = 0 # 初始站在地面高度 0
count = 0 # 记录需要添加的台阶数
for rung in rungs:
diff = rung - prev
if diff > dist:
count += (diff - 1) // dist
prev = rung
return count
📊 复杂度分析
- 时间复杂度:
O(n)
,只需遍历一遍rungs
数组; - 空间复杂度:
O(1)
,只用了常量级变量(prev
和count
)进行记录。
这使得该算法能够高效地处理输入规模达 10^5
的数据。
📎 示例说明(手动模拟)
示例:rungs = [1, 3, 5, 10], dist = 2
- 0 → 1:OK
- 1 → 3:OK
- 3 → 5:OK
- 5 → 10:差值为 5,需添加
(5-1)//2 = 2
个台阶 → 7, 9
最终添加台阶数:2 ✅
📚 分析和比较
✅ 优点:
- 实现简洁,逻辑清晰;
- 时间效率高,能应对大规模数据;
- 可以轻松扩展为 Java、C++、JavaScript 版本,适用于各类面试环境。
🚫 注意事项:
rungs
数组必须严格递增,否则题目本身不成立;- 不能遗漏与地面之间的第一跳;
- 插入台阶的位置不需要精确给出,只需知道数量即可。
🔁 拓展思考
若题目要求:
- 返回插入的台阶的实际高度,我们则需要维护一个新数组,在每次差值大于
dist
时,把所有中间台阶的高度计算出来; - 不允许插入新台阶怎么办?我们就要返回
-1
或类似错误处理。
✅ 总结
本题考察的是对区间距离的处理和贪心策略的应用:
- 贪心思想:每次尽量跳到能跳的最远距离;
- 区间分段:将距离
diff
分成不超过dist
的小段; - 算法技巧:用整数除法
//
快速计算插入数量,避免循环模拟。
这类题目虽然简单,但在面试中非常常见,建议熟练掌握。