range
约 812 字大约 3 分钟
2025-04-04
阅读导览
range
在 Python 中,通过 range 可以达到循环数字的效果:
- range(start, stop, step) 三个参数
- 顾头不顾腚:结果不包含 stop
- range 是惰性可迭代对象,不是列表
- 负步长可以反向生成序列
实践清单
学习练习清单
- 1分别跑 range(5)、range(1, 5)、range(0, 10, 2),确认 stop 永远不被包含。
- 2用 range(10, 0, -1) 生成递减序列,体会负步长的方向。
- 3对 range(10**8) 直接 print 和 len(),确认它不会一次性展开成列表。
- 4需要同时拿索引和元素时,试试 enumerate,而不是 range(len(seq))。
在 Python 中,通过 range 可以达到循环数字的效果:
python playground
for i in range(1, 5):
print(i)对于下面一行代码:
python playground
a = range(0, 5)
print(a)在 Python2 中,会打印出列表 [0, 1, 2, 3, 4];在 Python3 中则会被打印为 range(0, 5)。可以通过 list() 函数将 range 对象转化为列表:
python playground
a = range(0, 5)
print(list(a)) # [0, 1, 2, 3, 4]range 中的参数和 切片 极其相似,range 的索引是几,其对应的值就是几:
python playground
for i in range(0, 51, 2):
print(i) # 打印 0-50 间的所有偶数
for i in range(1, 51, 2):
print(i) # 打印 0-50 间的所有奇数range 与 切片 所不同的是,range 的终止位置为负数时,表示的是负数位置,而不是从右向左数的位置:
python playground
for i in range(10, -11, -1):
print(i) # 打印 10 到 -10 的数字一般情况下,我们可以直接写入一个终止位置。这时,起始位置默认为 0,步长默认为 1:
python playground
print(list(range(5))) # [0, 1, 2, 3, 4]需要注意,如果要设置步长,一定要把变量写全,要包含起始位置。
很显然,range 是一个可迭代对象
range 不是列表,而是惰性的可迭代对象
新手常误以为 range(n) 就是一个数字列表,其实它是一个惰性对象——只在被迭代时一个一个地算出来,不会一次性把所有数字放进内存。所以下面这段代码不会爆内存:
python playground
big = range(10**9) # 十亿,瞬间创建,几乎不占内存
print(len(big)) # 1000000000
print(big[500]) # 500,支持索引需要真正的列表时再 list(range(...)),但绝大多数 for 循环场景,直接用 range 既快又省内存。
同时要拿索引和元素时,用 enumerate
新手最容易写出这种代码:
for i in range(len(names)):
print(i, names[i])更地道的写法是 enumerate,它直接给你 (索引, 元素) 的元组:
python playground
names = ['alice', 'bob', 'tom']
for i, name in enumerate(names):
print(i, name)range(len(seq)) 几乎总有更好的替代——多数时候是 enumerate,遍历多个序列时是 zip。
重点总结
要点回收
- range 接收 start、stop、step 三个参数,遵循“顾头不顾腚”,结果不包含 stop。
- range 是惰性的可迭代对象,不会一次性占内存,适合大范围循环。
- 想同时拿索引和值时优先用 enumerate,比 range(len(seq)) 更地道。
版权所有
版权归属:Shuo Liu
