从函数内部停止迭代

时间:2017-09-26 12:40:16

标签: python iterator break

我正在使用迭代器灵活地浏览集合。在我的函数中,有几种情况,函数获取一个新项并处理它们。所以有几种情况会发生这样的事情:

it = iter(range(10))
while condition:
    try:
        item = next(it)
        item.do_many_different_things()
    except StopIteration:
        break

这使得一切都非常混乱,所以我想把它变成一个单独的方法。但是我不能使用break,因为python不知道它应该打破什么循环。到目前为止,我返回一个None类型,如果返回None,则中断循环。但是有更优雅的解决方案吗?

2 个答案:

答案 0 :(得分:0)

您可以从do_many_different_things()函数返回值并相应地更改condition变量,以便根据需要突破while循环。

def func(it):
    item = next(it)
    res = item.do_many_different_things()
    yield res

it = iter(range(1, 10))

condition = True
while condition:
    for item in func(it):
        condition = item

这将运行1..9中的所有元素,因为它们都是真实的。如果你使用常规range(10)开始它,它将停在第一个元素上,因为它是0。

方法返回False后,while循环中断。

答案 1 :(得分:0)

我不知道你的代码,嵌套循环和项目是什么,所以我将向你展示如何突破不同功能的嵌套循环。我还将向您展示如何区分三种情况:
1.您的item.do_many_different_things()方法想要破解 你的物品用完了 3.您的condition评估为False

这纯粹是教育性的,可以向您展示一些您可能觉得有用的Python功能,而不一定是这种精确组合。

from __future__ import print_function
# I'm on Python 3 - you will need the above line on Python 2

# I don't know what your code is supposed to do so I'll just generate random integers
from random import Random

r = Random()
r.seed()


class BreakOutNested(Exception): pass


class Item(object):

    def do_many_different_things(self):
        x = r.randint(0, 50)
        if x == 50:
            raise BreakOutNested()
        self.x = x


def iterator_0(item):
    for i in range(5):
        item.do_many_different_things()
        yield i

def iterator_1(items):
    for item in items:
        for i in iterator_0(item):
            item.i = i
            yield item


items = iterator_1(Item() for i in range(5))
x = 50

try:
    while x != 0:
        item = next(items)
        print(item.i, item.x)
        x = item.x
except BreakOutNested:
    print('Broke out from many loops with exception trick')
except StopIteration:
    print('Simply ran out of items')
else:
    print('Got x == 0')

运行此操作几次,因为退出方案是随机的。