只数循环用到的因子
循环体里累积量只被同一种运算反复作用(一路乘、一路除、一路加),那输出就是这种运算把「计数器取过的那些值」折起来的结果。于是不必逐轮跑,只要定出**哪些值真的被用过**这个集合。
解题套路
先看循环体对累积量做了什么。如果每一轮都是同一种运算、且另一个操作数就是计数器:
| 循环体 | 输出 |
|---|---|
乘法与加法都满足结合律、交换律,所以运算的先后次序完全不影响结果——逐轮模拟里那条「 怎么一步步变小」的轨迹是多余信息。 剩下唯一要定的是求和 / 求积的下标集合:计数器 究竟取过哪几个值,且每个值取过几次。
两步:
- 定集合。计数器一般是 起、每轮 。关键只有一句:哪一轮的运算真的做了。
- 判断框在循环体之后(先做后判):触发退出的那个 是在本轮运算做完之后才自增出来的, 所以它没有参与运算;参与的是它前面那些。
- 判断框在循环体之前(先判再做):被判断拦住的那个 同样没参与。
- 折起来。把集合里的值按那一种运算连乘 / 连加。
为什么值得单独当一条路
它和「找循环不变式」是两回事:不变式要写出闭式再归纳,这条连闭式都不用—— 就是答案,认不出它等于 也不影响作答。 它也是三条路里最容易自查的一条:数一遍集合的元素个数,就等于循环跑过的轮数。
什么时候不能用
- 循环体里累积量与自己纠缠(:这一轮的 会被后面每一轮再乘一次 , 次序有意义,折不起来);
- 循环体里有分支,某些轮做乘、某些轮做加;
- 计数器的更新依赖累积量( 的步长与 有关),集合本身要跑才知道。
前两种老老实实逐轮跑或写递推。
一个提醒
「集合」二字要当真:取过几次也算。若一轮里计数器被用了两次(如 ), 或者步长使某个值被跳过,连乘式里的因子就与「 到某个上限的全部整数」不是一回事。 写连乘之前,把因子一个一个念出来,别写 就以为完事。
学它之前先会
共 1 条前置、最深 1 层。
出现在以下题目中
共 1 道题考到本条。