strange list comprehension on generator

Discussion in 'Python' started by Roland Puntaier, Aug 29, 2007.

  1. def changeOne(aa,idx):
    aa[idx]=not aa[idx]
    yield aa
    for i in range(idx):
    for x in changeOne(aa,i):
    yield x

    def changeOneOrder(aa):
    yield aa
    for i in range(len(aa)):
    for x in changeOne(aa,i):
    yield x

    a=[False]*3
    og=changeOneOrder(a)
    #this does not return the way I would expect. why?
    list(og)
    #returns
    #[[False, False, True], [False, False, True], [False, False, True],
    [False, False, True], [False, False, True], [False, False, True], [False,
    False, True], [False, False, True]]


    #this works as expected
    a=[False]*3
    og=changeOneOrder(a)
    og.next()
    og.next()
    ....

    #this works as expected
    def ty():
    yield 1
    yield 2
    yield 3

    tg=ty()
    list(tg)

    cheers, Roland
     
    Roland Puntaier, Aug 29, 2007
    #1
    1. Advertising

  2. No greeting, no text? Pity.

    Roland Puntaier wrote:

    > def changeOne(aa,idx):
    > aa[idx]=not aa[idx]
    > yield aa
    > for i in range(idx):
    > for x in changeOne(aa,i):
    > yield x
    >
    > def changeOneOrder(aa):
    > yield aa
    > for i in range(len(aa)):
    > for x in changeOne(aa,i):
    > yield x


    Okay, two generator definitions.

    > a=[False]*3
    > og=changeOneOrder(a)
    > #this does not return the way I would expect. why?


    What do you expect? You created a generator object and bound it
    to "og".

    Please always state what you expect and what really happens. Fortune
    telling is not one of my hobbies (and I think I'm not alone with
    that).

    Regards,


    Björn

    --
    BOFH excuse #284:

    Electrons on a bender
     
    Bjoern Schliessmann, Aug 29, 2007
    #2
    1. Advertising

  3. > #this does not return the way I would expect. why?

    You yield the very same list object all the times. So
    when you make a later change, all earlier results will
    get changed, too (since they are the same object).
    Of course, it won't affect the terminal output, so you
    don't see that the older values changed in the example
    that you think works as expected.

    HTH,
    Martin
     
    =?ISO-8859-1?Q?=22Martin_v=2E_L=F6wis=22?=, Aug 29, 2007
    #3
  4. > #this does not return the way I would expect. why?

    You yield the very same list object all the times. So
    when you make a later change, all earlier results will
    get changed, too (since they are the same object).
    Of course, it won't affect the terminal output, so you
    don't see that the older values changed in the example
    that you think works as expected.

    HTH,
    Martin
     
    =?ISO-8859-1?Q?=22Martin_v=2E_L=F6wis=22?=, Aug 29, 2007
    #4
  5. Roland Puntaier

    Guest

    On Aug 29, 6:50 am, Roland Puntaier <Roland.Punta...@br-
    automation.com> wrote:
    > def changeOne(aa,idx):
    > aa[idx]=not aa[idx]
    > yield aa
    > for i in range(idx):
    > for x in changeOne(aa,i):
    > yield x
    >
    > def changeOneOrder(aa):
    > yield aa
    > for i in range(len(aa)):
    > for x in changeOne(aa,i):
    > yield x
    >
    > a=[False]*3
    > og=changeOneOrder(a)
    > #this does not return the way I would expect. why?
    > list(og)
    > #returns
    > #[[False, False, True], [False, False, True], [False, False, True],
    > [False, False, True], [False, False, True], [False, False, True], [False,
    > False, True], [False, False, True]]



    If you want the "intermediate" states of 'a' in
    list(og), then you need to yield a copy of that list,
    instead of the list itself:

    def changeOne(aa, idx):
    aa[idx] = not aa[idx]
    yield aa[:] # <------- a copy
    for i in range(idx):
    for x in changeOne(aa, i):
    yield x

    def changeOneOrder(aa):
    yield aa[:] # <------- a copy
    for i in range(len(aa)):
    for x in changeOne(aa, i):
    yield x

    a = [False] * 3
    og = changeOneOrder(a)
    print list(og)

    Otherwise, as you've already noticed, you can
    loop over the iterator and do something
    with the "instantaneous" state of 'a'.

    --
    Hope this helps,
    Steven
     
    , Aug 29, 2007
    #5
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. George Henry

    Strange (?) list comprehension behavior

    George Henry, Jul 19, 2003, in forum: Python
    Replies:
    3
    Views:
    433
    Peter Hansen
    Jul 20, 2003
  2. Steven W. Orr
    Replies:
    2
    Views:
    334
    Scott David Daniels
    Apr 21, 2007
  3. Debajit Adhikary
    Replies:
    17
    Views:
    720
    Debajit Adhikary
    Oct 18, 2007
  4. Vedran Furac(
    Replies:
    4
    Views:
    356
    Marc 'BlackJack' Rintsch
    Dec 19, 2008
  5. candide
    Replies:
    3
    Views:
    429
    candide
    Sep 20, 2009
Loading...

Share This Page