循环优化核心是将不变表达式移出循环体。需手动提取循环外不变量(如len、函数调用、方法绑定),优先使用生成器/内置函数(any、sum等),对纯函数用@lru_cache缓存,改用手动索引为enumerate/zip。

循环中避免重复计算,核心是把不变的表达式移出循环体。Python解释器不会自动帮你做这件事,得靠自己识别和重构。
提前计算循环外不变量
如果某个值在每次迭代中都不变,比如函数调用结果、数学常量、对象属性或列表长度,就别让它待在 for 或 while 里面反复算。
常见例子:
-
列表长度:用
len(lst)做循环条件?先存成变量再用。 -
函数返回值:如
math.sqrt(2)或config.get('timeout'),只调一次。 -
字符串方法绑定:
line.strip()在循环里频繁调用?可提前绑定stripper = str.strip,再用stripper(line)。
用生成器或推导式替代显式循环
很多“边算边用”的场景,其实不需要完整列表。生成器表达式((x*2 for x in data))比列表推导式([x*2 for x in data])更省内存;而内置函数如 sum()、any()、all() 内部已优化,比手写循环快。
立即学习“Python免费学习笔记(深入)”;
例如:
- 判断是否存在满足条件的元素 → 用
any(x > 10 for x in data),而非写for+break。 - 求平方和 → 用
sum(x**2 for x in data),而不是先建列表再sum()。
缓存重复调用的函数结果
如果循环中反复调用同一函数、且参数组合有限,加个 @lru_cache 能显著提速,尤其适合递归或纯计算函数。
注意点:
- 只对 纯函数(无副作用、输入决定输出)有效。
- 参数必须可哈希(如不能传列表、字典等可变类型)。
- 缓存大小设为
None表示不限,但要警惕内存占用。
用 enumerate 和 zip 减少索引操作
手动维护下标(如 i = 0; i += 1)易出错又低效;用 range(len(...)) 访问元素还多一次索引查找。
更优写法:
- 需要索引和值 → 直接
for i, item in enumerate(items): - 遍历多个等长序列 → 用
for a, b in zip(list_a, list_b):,不需反复写list_a[i]和list_b[i] - 避免
items[i]查找开销,尤其是自定义类或大对象时更明显。
不复杂但容易忽略。关键不是写得多快,而是让 Python 少做几次一样的事。









