Search code examples
pythonpython-itertools

Fast Forward an xrange from Nested Loop Using Dropwhile?


I have seen related posts but not quite this question. I am looking for a way to fast forward an iterator in an outer loop without calling next() in a loop.

The answer may simply be to use the same iterator in the inner loop but I thought there might be a nice way with itertools, I am using dropwhile() but it's not doing what I expected.

So I have a loop inside a loop:

cl = ['a', 'b', 'c', 'd', 'e']
rangeiter = xrange(0, len(cl))
for x in rangeiter:
    print('{}-'.format(x)),
    for y in xrange(x, len(cl)):
        print('{}'.format(cl[y])),
        if y == 3:
            print
            break
    # fast forward parent range
    rangeiter = dropwhile(lambda v: v < y, rangeiter)

I want the outer loop to skip past any indices that the inner loop has processed. I thought that dropwhile would have done this, but instead I am getting:

0- a b c d
1- b c d
2- c d
3- d
4- e

when i wanted

0- a b c d
4- e

The code is here.

Thanks!


Solution

  • The for loop creates an iterator for iterables; xrange() is a sequence (an iterable), not an iterator.

    Create the iterator explicitly, then advance that by using dropwhile() (iterating over that object!) to skip elements:

    cl = ['a', 'b', 'c', 'd', 'e']
    rangeiter = iter(xrange(0, len(cl)))
    for x in rangeiter:
        print('{}-'.format(x)),
        for y in xrange(x, len(cl)):
            print('{}'.format(cl[y])),
            if y == 3:
                print
                break
        # fast forward parent range
        next(dropwhile(lambda v: v < y, rangeiter), None)
    

    Note that dropwhile I adjusted your dropwhile condition to advance based on y, not x; your expected output suggests you wanted to advance the outer range to beyond where the inner loop had gotten to.