Python 向下枚举或使用自定义步骤

问题描述 投票:0回答:6

如何使Python的

enumerate
函数从大到小进行枚举(降序、递减、倒数)?或者一般来说,如何在
enumerate
中使用不同的步长增量/减量?

例如,这样的函数应用于列表

['a', 'b', 'c']
,起始值
10
和步骤
-2
,将产生迭代器
[(10, 'a'), (8, 'b'), (6, 'c')]

python enumerate
6个回答
33
投票

我还没有找到比编写一个简单的生成器更优雅、更惯用、更简洁的方法:

def enumerate2(xs, start=0, step=1):
    for x in xs:
        yield (start, x)
        start += step

示例:

>>> list(enumerate2([1,2,3], 5, -1))
[(5, 1), (4, 2), (3, 3)]
>>> list(enumerate2([1,2,3], 5, -2))
[(5, 1), (3, 2), (1, 3)]

如果你不明白上面的代码,请阅读“yield”关键字在Python中做什么?Python的生成器和迭代器之间的区别


10
投票

一种选择是

zip
将您的可迭代对象转换为
range
:

for index, item in zip(range(10, 0, -2), ['a', 'b', 'c']):
    ...

这确实有一个限制,您需要知道

range
应该走多远(它应该覆盖的最小值 - 正如在我的示例中,超出的部分将被
zip
截断)。

如果你不知道,你可以滚动你自己的“无限

range
”(或者只使用
itertools.count
)并使用它:

>>> def inf_range(start, step):
    """Generator function to provide a never-ending range."""
    while True:
        yield start
        start += step

        
>>> list(zip(inf_range(10, -2), ['a', 'b', 'c']))
[(10, 'a'), (8, 'b'), (6, 'c')]

3
投票

这是一种惯用的方法:

list(zip(itertools.count(10,-2), 'abc'))

返回:

[(10, 'a'), (8, 'b'), (6, 'c')]


2
投票

另一种选择是使用

itertools.count
,这有助于通过 stepreverse 中“枚举”。

import itertools

counter = itertools.count(10, -2)
[(next(counter), letter) for letter in ["a", "b", "c"]]
# [(10, 'a'), (8, 'b'), (6, 'c')]

特点

  • 简洁
  • 步长和方向逻辑紧凑地存储在
    count()
  • 枚举索引用
    next()
  • 进行迭代
  • count()
    本质上是无限的;如果终端边界未知,则很有用 (参见@jonrsharpe)
  • 序列长度本质上终止了无限迭代器

0
投票

如果您不需要将迭代器保存在变量中而只需迭代某个容器,请将索引乘以步骤。

container = ['a', 'b', 'c']
step = -2

for index, value in enumerate(container):
    print(f'{index * step}, {value}')


>>> 0, a
-2, b
-4, c

-1
投票

可能不是很优雅,使用f'strings以下快速解决方案可以很方便

my_list = ['apple', 'banana', 'grapes', 'pear']
p=10
for counter, value in enumerate(my_list):
    print(f" {counter+p}, {value}")
    p+=9

> 10, apple
> 20, banana
> 30, grapes
> 40, pear
© www.soinside.com 2019 - 2024. All rights reserved.