iterator? way of generating all possible combinations?

Jim Segrave jes at nl.demon.net
Wed May 31 10:32:01 EDT 2006


In article <447cadf6$1 at nntp0.pdx.net>,
Scott David Daniels  <scott.daniels at acm.org> wrote:
>
>This works if-and-only-if it is only in use once at a time.
>If you have multiple simultaneous accesses, you need to do
>something like:
>
>     class FileReIterable2(object):
>         def __init__(self, file):
>             if isinstance(file, basestring):
>                 self.file = open(file, 'rU')
>             else:
>                 self.file = file
>         def __iter__(self):
>             self.file.seek(0)
>             for line in self.file:
>                 nextpos = self.file.tell()
>                 yield line
>                 self.file.seek(nextpos)

Hmm - I tried this with 'one.file' being just the lower case letters,
one per line:

class FileReIterable2(object):
    def __init__(self, file):
        if isinstance(file, basestring):
            self.file = open(file, 'rU')
        else:
            self.file = file


    def __iter__(self):
        self.file.seek(0)
        for line in self.file:
            nextpos = self.file.tell()
            yield line
            self.file.seek(nextpos)


gen = FileReIterable2("one.file")

for a in gen:
    for b in gen:
        print "    ", a.strip(), b.strip()


gen = FileReIterable2("one.file")
for a in gen:
  for b in gen:
    print a.strip(), b.strip()

which didn't produce lines 'a a', 'a b', etc. It produced the single
line 'a a', then stopped. A judicious proint or two showed that after
the first execution of 'for line in self.file:', the file pointer was
at EOF, not at 2, as one would expect.

Rewriting the __iter__ method to not internally iterate over the file
object, as follows, works - it now generates
a a
...
a z
b a
...
z z


class FileReIterable2(object):
    def __init__(self, file):
        self.file = open(file, 'rU')

    def __iter__(self):
        self.file.seek(0)
        while True:
            line = self.file.readline()
            if line == '': raise StopIteration
            nextpos = self.file.tell()
            yield line
            self.file.seek(nextpos)



-- 
Jim Segrave           (jes at jes-2.demon.nl)




More information about the Python-list mailing list