469,338 Members | 8,430 Online
Bytes | Developer Community
New Post

Home Posts Topics Members FAQ

Post your question to a community of 469,338 developers. It's quick & easy.

'while' in list comprehension?

Hi there,

wouldn't it be useful to have a 'while' conditional in addition to
'if' in list comprehensions?

foo = []
for i in bar:
if len(i) == 0:
break
foo.append(i)

would then turn into

foo = [ i for i in bar while len(i)>0 ]

Is there any reason for not having this kind of thing? I actually
miss it pretty often.

Cheers, jsaul
Jul 18 '05 #1
14 13605
jsaul asks...
would then turn into

foo = [ i for i in bar while len(i)>0 ]

Is there any reason for not having this kind of thing? I actually
miss it pretty often.

How is this different from:

foo = [ i for i in bar if len(i) ]

Emile van Sebille
em***@fenx.com
Jul 18 '05 #2
foo = [ i for i in bar while len(i)>0 ]


Emile> How is this different from:

Emile> foo = [ i for i in bar if len(i) ]

The first is like:

_ = []
for i in bar:
if not (len(i) > 0):
break
_.append(i)
return _

The second is like:

_ = []
for i in bar:
if len(i) > 0:
_.append(i)
return _

Skip

Jul 18 '05 #3
Use 2.3's itertools:
foo = [i for i in itertools.takewhile(lambda i: len(i) > 0, bar)]
or maybe
foo = list(itertools.takewhile(len, bar)]
or even
foo = itertools.takewhile(len, bar) # an iterable, not a list

Jeff

Jul 18 '05 #4
At 01:05 PM 10/22/2003, Emile van Sebille wrote:
jsaul asks...
would then turn into

foo = [ i for i in bar while len(i)>0 ]

Is there any reason for not having this kind of thing? I actually
miss it pretty often.

How is this different from:

foo = [ i for i in bar if len(i) ]


My reading is that the comprehension would stop at the first i whose len
were 0. e.g.
foo = []
for i in bar:
if len(i) == 0:break
foo.append(i)

Bob Gailer
bg*****@alum.rpi.edu
303 442 2625
---
Outgoing mail is certified Virus Free.
Checked by AVG anti-virus system (http://www.grisoft.com).
Version: 6.0.525 / Virus Database: 322 - Release Date: 10/9/2003

Jul 18 '05 #5
"Emile van Sebille" <em***@fenx.com> wrote in message
news:bn************@ID-11957.news.uni-berlin.de...
jsaul asks...
would then turn into

foo = [ i for i in bar while len(i)>0 ]

Is there any reason for not having this kind of thing? I actually
miss it pretty often.

How is this different from:

foo = [ i for i in bar if len(i) ]

Emile van Sebille
em***@fenx.com


The idea is that 'while' stops iterating through the list when the condition
isn't met. 'if' just doesn't output anything. e.g.:
bar = ['this', 'is', 'a', 'list', '', 'see?']
[i for i in bar if len(i)] ['this', 'is', 'a', 'list', 'see?'] [i for i in bar while len(i)] # Pretend

['this', 'is', 'a', 'list']

What's your typical use for this?

I guess I see nothing really wrong with it, although I thought list
comprehensions were supposed to make the iteration transparent--'while'
kinda destroys the illusion. But these are the only two looping constructs
that make sense in a list comprehension, so why not support both? OTOH,
'while' makes no sense in a dictionary comprehension (and presumably we'll
have those one day.)

Jul 18 '05 #6
jsaul <js***@gmx.de> wrote in message news:<20********************@jsaul.de>...

foo = [ i for i in bar while len(i)>0 ]

Is there any reason for not having this kind of thing? I actually
miss it pretty often.


Could you provide an example where you need it?

From your message, it seems "bar" might be a list of strings. If so, you could use:

foo = bar[:bar.index('')]

regards,

Hung Jung
Jul 18 '05 #7

"jsaul" <js***@gmx.de> wrote in message
news:20********************@jsaul.de...
Hi there,

wouldn't it be useful to have a 'while' conditional in addition to
'if' in list comprehensions?

foo = []
for i in bar:
if len(i) == 0:
break
foo.append(i)

would then turn into

foo = [ i for i in bar while len(i)>0 ]


while is simply not same as if: break!
if executes once for each value of i, while indefinitely.
If you translate back by current rule, which will not change, you get:

foo = []
for i in bar:
while len(i) >0:
foo.append(i)

Terry J. Reedy
Jul 18 '05 #8
On Wed, 22 Oct 2003 22:57:42 -0400, "Terry Reedy" <tj*****@udel.edu>
wrote:
while is simply not same as if: break!
if executes once for each value of i, while indefinitely.
If you translate back by current rule, which will not change, you get:


'while' is an English word which has meaning independant of the
existing Python 'while' loop. It is not necessarily wrong to apply a
different aspect of that meaning in a list comprehension.

Besides, I read the syntax as equating to...

foo = []
for i in bar while len(i) >0:
foo.append(i)

Yes, I know that isn't a legal Python loop. My point is that it didn't
look like a nested loop to me, but rather like an additional qualifier
on the existing loop.

That said, you do have a point - multiple 'for' parts in a list
comprehension act as nested loops, so maybe a while part should too.

The trouble is that a standalone while loop probably makes little
sense in a list comprehension - sure you have a place to put the loop
condition, but what about the initialisation and body?

If there were a real while-part in a list comprehension, it would
probably need those things to become explicit (becoming a lot like the
C for loop) - something like...

[k while k=1; k<1024; k*=2]

Hmmmm...

while i=0; i<10; i++ :
print i

Hmmmm....

Nah - damn silly idea.
--
Steve Horne

steve at ninereeds dot fsnet dot co dot uk
Jul 18 '05 #9
* Terry Reedy [2003-10-23 04:57]:
"jsaul" <js***@gmx.de> wrote in message
news:20********************@jsaul.de...
wouldn't it be useful to have a 'while' conditional in addition to
'if' in list comprehensions?

foo = []
for i in bar:
if len(i) == 0:
break
foo.append(i)

would then turn into

foo = [ i for i in bar while len(i)>0 ]


while is simply not same as if: break!
if executes once for each value of i, while indefinitely.
If you translate back by current rule, which will not change, you get:

foo = []
for i in bar:
while len(i) >0:
foo.append(i)


I agree that 'while' cannot not just be considered a replacement
for 'if'. However, adding a 'while' conditional to list
comprehensions would very unlikely be misunderstood as another
(infinite) loop. Instead, I find the above 'while' example about
as intuitive as is the case with 'if'. It simply means that under
a certain condition the loop will be ended, which is just what
most people would probably expect.

Anyway, thanks a lot to all who replied! What is your opinion
after this discussion, write a PEP or just forget about it?

Cheers, jsaul
Jul 18 '05 #10
> > > wouldn't it be useful to have a 'while' conditional in addition to
'if' in list comprehensions?

foo = []
for i in bar:
if len(i) == 0:
break
foo.append(i)

would then turn into

foo = [ i for i in bar while len(i)>0 ]


while is simply not same as if: break!
if executes once for each value of i, while indefinitely.
If you translate back by current rule, which will not change, you get:

foo = []
for i in bar:
while len(i) >0:
foo.append(i)


I agree that 'while' cannot not just be considered a replacement
for 'if'. However, adding a 'while' conditional to list
comprehensions would very unlikely be misunderstood as another
(infinite) loop. Instead, I find the above 'while' example about
as intuitive as is the case with 'if'. It simply means that under
a certain condition the loop will be ended, which is just what
most people would probably expect.


Here's an idea that might avoid this bit of confusion:

foo = [ i for i in bar until len(i) == 0 ]

That also makes the conditional test the same as used in the "if/break"
form.

Hmm... Would this mean that "until" would have to become a reserved word?
Maybe not such a good idea if that's the case.

-Mike
Jul 18 '05 #11
Jeff Epler <je****@unpythonic.net> wrote in message news:<ma***********************************@python .org>...
Use 2.3's itertools:
foo = [i for i in itertools.takewhile(lambda i: len(i) > 0, bar)]
or maybe
foo = list(itertools.takewhile(len, bar)]
or even
foo = itertools.takewhile(len, bar) # an iterable, not a list


or list(takewhile(len, bar))

from itertools import * :)

Andrae
Jul 18 '05 #12
"Michael Geary" <Mi**@DeleteThis.Geary.com> wrote in message news:<vp************@corp.supernews.com>...
Here's an idea that might avoid this bit of confusion:

foo = [ i for i in bar until len(i) == 0 ]


Another variation:

foo = [i for i in bar, break if len(i) == 0]

This wouldn't need a new keyword.
Jul 18 '05 #13
Hannu Kankaanp?? wrote:
Another variation:

foo = [i for i in bar, break if len(i) == 0]

This wouldn't need a new keyword.


My thoughts on all this are that if you want to do
something that procedural, it would be better written
out as nested statements. List comprehensions are
meant to be read declaratively.

--
Greg Ewing, Computer Science Dept,
University of Canterbury,
Christchurch, New Zealand
http://www.cosc.canterbury.ac.nz/~greg

Jul 18 '05 #14
Greg Ewing (using news.cis.dfn.de) wrote:
Hannu Kankaanp?? wrote:
Another variation:

foo = [i for i in bar, break if len(i) == 0]

This wouldn't need a new keyword.


My thoughts on all this are that if you want to do
something that procedural, it would be better written
out as nested statements. List comprehensions are
meant to be read declaratively.


Yes, they are. Still,

[ i for i in bar while len(i) ]

DOES read pretty declaratively to me (while the "break"
version admittedly doesn't).
Alex

Jul 18 '05 #15

This discussion thread is closed

Replies have been disabled for this discussion.

Similar topics

23 posts views Thread by Fuzzyman | last post: by
35 posts views Thread by Moosebumps | last post: by
6 posts views Thread by jena | last post: by
21 posts views Thread by Daniel Schüle | last post: by
18 posts views Thread by a | last post: by
4 posts views Thread by Gregory Guthrie | last post: by
12 posts views Thread by Eighty | last post: by
reply views Thread by zhoujie | last post: by
reply views Thread by suresh191 | last post: by
reply views Thread by Purva khokhar | last post: by
By using this site, you agree to our Privacy Policy and Terms of Use.