End of file
Alex Martelli
aleaxit at yahoo.com
Thu Oct 7 09:44:08 EDT 2004
Andreas Kostyrka <andreas at kostyrka.org> wrote:
...
> > for counter, line in enumerate(f):
> > if counter == lines-1: is_last_line(line)
> > else: is_ordinary_line(line)
> >
> > If the file's possibly too big to read comfortably in memory, of course,
> > other suggestions based on generators &c are preferable.
> This should do it "right":
>
> f = file("/etc/passwd")
> fi = iter(f)
>
> def inext(i):
> try:
> return i.next()
> except StopIteration:
> return StopIteration
>
> next = inext(fi)
> while next <> StopIteration:
> line = next
> next = inext(fi)
> if next == StopIteration:
> print "LAST USER", line.rstrip()
> else:
> print "NOT LAST", line.rstrip()
I think the semantics are correct, but I also believe the control
structure in the "application code" is too messy. A generator lets you
code a simple for loop on the application side of things, and any
complexity stays where it should be, inside the generator. Haven't read
the other posts proposing generators, but something like:
def item_and_lastflag(sequence):
it = iter(sequence)
next = it.next()
for current in it:
yield next, False
next = current
yield next, True
lets you code, application-side:
for line, is_last in item_and_lastflag(open('/etc/passwd')):
if is_last: print 'Last user:', line.rstrip()
else print: 'Not last:', line.rstrip()
Not only is the application-side loop crystal-clear; it appears to me
that the _overall_ complexity is decreased, not just moved to the
generator.
Alex
More information about the Python-list
mailing list