题目重点:汇总帖给出按最左非零 x 向右连续减值、遇较小值停并累加 x 的步骤;先实现字面规则,再讨论复杂度。
题意与假设
这道练习题保留了面经中值得训练的核心约束,并将需要澄清的条件单独列出。现场拿到变体时,先和面试官确认这些条件。
- 数组元素为非负整数;若含负数,‘最左非零’和‘小于 x’会改变终止性,题目未明确。
- 每轮从最左正数所在位置开始,向右对连续 ≥x 的元素各减 x;遇第一个 <x 即停,随后 ans+=x,再从头找最左正数,直到全零。
- ‘到达最后一位结束’解释为本轮扫描结束,而非整个算法立即停止;否则示例与输出可能不一致。
解题路线
- 基线按文字执行:扫描找最左正数 i,取 x=a[i];从 i 向右 while a[j]≥x,减去 x,遇较小值 break;把 x 加入 ans。
- 每轮至少把 a[i] 变成 0,所以下次最左正数下标严格向右移动;最多 n 轮,不会因为后续被减值后又回到早期位置。
- 直接数组实现每轮最坏扫剩余前缀,最坏 O(n²);若题目数据规模很大再分析数据结构优化,题目没有约束,不应凭猜测用排序替换顺序。
- 检查全零、单值、内部 0、非降序和交替高低值;对照独立规则模拟。
手动走一遍
题目 [3,5,5,1]:第一轮 x=3,数组变 [0,2,2,1],ans=3;第二轮 x=2,变 [0,0,0,1],ans=5;第三轮 x=1,变全零,ans=6。训练反例 [3,1,5] 中第一轮遇 1 即停,不能越过它去减 5。
规模与取舍
最多 n 轮,每轮线性扫描,因此朴素实现 O(n²) 时间、O(1) 额外空间;答案最大为初始元素总和,需要按输入上界选择整数类型。题目提超时但未披露 n,不能断定 O(n²) 达标。
易错点与追问
容易失分的边界
- 越过小于 x 的元素继续减值。
- 将 x 从所有 ≥x 的位置扣除,忽略连续边界。
- 到达数组末尾后提前返回而仍有正数。
- 把数组排序后处理,破坏原相邻顺序。
- 未核实负数输入。
继续深挖
- 能否利用区间最小值和懒惰更新优化?
- 若题目要求每轮操作数而非 x 的总和如何改?
- 如果遇到 x 相等的元素是否继续?
- 对题目‘到末尾结束’应如何澄清?
