Idiomatic way of repeating items in a sequence.

Discussion in 'Python' started by alr, Jun 30, 2003.

  1. alr

    alr Guest

    I need to repeat each item in a list n times, like this function does:

    def repeatitems(sequence, repetitions):
    newlist = []
    for item in sequence:
    for i in range(repetitions):
    newlist.append(item)
    return newlist

    Output:

    >>> repeatitems(['a', 'b', 'c'], 3)

    ['a', 'a', 'a', 'b', 'b', 'b', 'c', 'c', 'c']

    Clear and simple. But i wonder if there is a more idiomatic way. Surely not this:

    def repeatitems(sequence, repetitions):
    return reduce(lambda l, i: l + i, [[item] * repetitions for item in sequence])

    ?
     
    alr, Jun 30, 2003
    #1
    1. Advertising

  2. alr

    Max M Guest

    alr wrote:
    > I need to repeat each item in a list n times, like this function does:
    >
    > def repeatitems(sequence, repetitions):
    > newlist = []
    > for item in sequence:
    > for i in range(repetitions):
    > newlist.append(item)
    > return newlist



    I would make just a minor change:

    def repeatitems(sequence, repetitions):
    newlist = []
    for item in sequence:
    newlist += repetitions*[item]
    return newlist


    regards Max M
     
    Max M, Jun 30, 2003
    #2
    1. Advertising

  3. alr

    Duncan Booth Guest

    (alr) wrote in
    news::

    > I need to repeat each item in a list n times, like this function does:
    >
    > def repeatitems(sequence, repetitions):
    > newlist = []
    > for item in sequence:
    > for i in range(repetitions):
    > newlist.append(item)
    > return newlist
    >
    > Output:
    >
    > >>> repeatitems(['a', 'b', 'c'], 3)

    > ['a', 'a', 'a', 'b', 'b', 'b', 'c', 'c', 'c']
    >
    > Clear and simple. But i wonder if there is a more idiomatic way.


    The most obvious one that springs to mind is just a slight simplification
    of your version:

    def repeatitems(sequence, repetitions):
    newlist = []
    for item in sequence:
    newlist.extend([item] * repetitions)
    return newlist


    --
    Duncan Booth
    int month(char *p){return(124864/((p[0]+p[1]-p[2]&0x1f)+1)%12)["\5\x8\3"
    "\6\7\xb\1\x9\xa\2\0\4"];} // Who said my code was obscure?
     
    Duncan Booth, Jun 30, 2003
    #3
  4. alr

    Peter Otten Guest

    alr wrote:

    > I need to repeat each item in a list n times, like this function does:
    >
    > def repeatitems(sequence, repetitions):
    > newlist = []
    > for item in sequence:
    > for i in range(repetitions):
    > newlist.append(item)
    > return newlist
    >

    ....
    > But i wonder if there is a more idiomatic way.


    How about this?

    def repeatItems(sequence, repetitions):
    return [[item]*repetitions for item in sequence]
     
    Peter Otten, Jun 30, 2003
    #4
  5. "Peter Otten" <> wrote in message news:bdpdd7$iue$00$-online.com...

    > How about this?
    >
    > def repeatItems(sequence, repetitions):
    > return [[item]*repetitions for item in sequence]


    Unfortunately that is equivalent to:

    def repeatitems(sequence, repetitions):
    newlist = []
    for item in sequence:
    newlist.append([item] * repetitions)
    return newlist

    and not:

    def repeatitems(sequence, repetitions):
    newlist = []
    for item in sequence:
    newlist.extend([item] * repetitions)
    return newlist
     
    Richard Brodie, Jun 30, 2003
    #5
  6. alr

    Duncan Booth Guest

    Duncan Booth <> wrote in
    news:Xns93AA81EC76E7Eduncanrcpcouk@127.0.0.1:

    > The most obvious one that springs to mind is just a slight
    > simplification of your version:
    >
    > def repeatitems(sequence, repetitions):
    > newlist = []
    > for item in sequence:
    > newlist.extend([item] * repetitions)
    > return newlist
    >


    Or, if you are in a "I've got a new toy to play with" mood you could use
    itertools from Python 2.3 to obfuscate it somewhat:

    from itertools import chain, izip, repeat
    def repeatiterate(sequence, repetitions):
    return chain(*izip(*repeat(sequence, repetitions)))

    This version returns an iterator, so you might want to throw in a call to
    'list' if you want to do anything other than iterating over the result.

    --
    Duncan Booth
    int month(char *p){return(124864/((p[0]+p[1]-p[2]&0x1f)+1)%12)["\5\x8\3"
    "\6\7\xb\1\x9\xa\2\0\4"];} // Who said my code was obscure?
     
    Duncan Booth, Jun 30, 2003
    #6
  7. alr

    Peter Otten Guest

    Richard Brodie wrote:

    > Unfortunately that is equivalent to:
    >
    > def repeatitems(sequence, repetitions):
    > newlist = []
    > for item in sequence:
    > newlist.append([item] * repetitions)
    > return newlist
    >


    .... but it looked so good. I should have tested it, though.
    Je suis desole :-(
     
    Peter Otten, Jun 30, 2003
    #7
  8. alr

    Terry Reedy Guest

    "alr" <> wrote in message
    news:...
    > I need to repeat each item in a list n times, like this function

    does:

    Is this really the right question? Any code that requires such an
    n-repeat list *could* be rewritten (if you own it) to use the replist
    in condensed form: (items, n). If this is not possible, one could
    also define a replist class with a __getitem__(self, index) that
    divides index by self.n and an __iter__() that returns an appropriate
    generator.

    Terry J. Reedy
     
    Terry Reedy, Jun 30, 2003
    #8
  9. alr

    John Hunter Guest

    >>>>> "alr" == alr <> writes:

    alr> reduce(lambda l, i: l + i, [[item] * repetitions for item in

    This doesn't look too bad to me, but perhaps list comprehensions are
    clearer?

    seq = ['a', 'b', 'c']
    print [x for x in seq for x in seq]
     
    John Hunter, Jun 30, 2003
    #9
  10. alr

    John Hunter Guest

    >>>>> "alr" == alr <> writes:

    alr> reduce(lambda l, i: l + i, [[item] * repetitions for item in
    alr> sequence])


    Oops, premature hit of send key. What I meant to say was

    seq = ['a', 'b', 'c']
    print [x for x in seq for i in range(len(seq))]

    JDH
     
    John Hunter, Jun 30, 2003
    #10
  11. alr

    Jeff Epler Guest

    Here's one:

    def repeatitems(sequence, repetitions):
    r = [None] * repetitions
    return [i for i in sequence for j in r]

    Here's another, using generator functions (so the return is an iterator,
    not a list):

    def repeatitems(sequence, repetitions):
    r = [None] * repetitions
    for item in sequence:
    for i in r:
    yield item

    In both cases I've performed an "optimization" by precomputing a list
    with len(repetitions) instead of computing it once for each item in
    sequence. Whether this makes a difference, I don't know.

    Jeff
     
    Jeff Epler, Jun 30, 2003
    #11
  12. John Hunter wrote:

    >This doesn't look too bad to me, but perhaps list comprehensions are
    >clearer?
    >
    > seq = ['a', 'b', 'c']
    > print [x for x in seq for x in seq]
    >
    >>> def repeat3( sequence, count=1 ):

    .... return [x for x in sequence for i in range(count) ]
    ....
    >>> repeat3( [2,3,4], 3 )

    [2, 2, 2, 3, 3, 3, 4, 4, 4]

    I *think* is what you were suggesting, and is indeed very clear. For
    those into generators, this is fun (but has no huge advantage if you
    wind up using repeat instead of irepeat, or if you're using small
    sequences):

    >>> from __future__ import generators
    >>> def irepeat( sequence, count=1 ):

    .... countSet = range(count)
    .... for item in sequence:
    .... for i in countSet:
    .... yield item
    ....
    >>> def repeat( sequence, count = 1 ):

    .... return list(irepeat(sequence, count))
    ....
    >>> repeat( [2,3,4], 3 )

    [2, 2, 2, 3, 3, 3, 4, 4, 4]

    Enjoy,
    Mike

    _______________________________________
    Mike C. Fletcher
    Designer, VR Plumber, Coder
    http://members.rogers.com/mcfletch/
     
    Mike C. Fletcher, Jun 30, 2003
    #12
  13. alr

    alr Guest

    Wow, tanks for alle the replies. My favourite is John Hunters/Bob
    Gailers solution ([x for x in seq for i in range(repetitions)]). I had
    forgotten that you could have nested for statements in list
    literals... Aahz's point is taken. I happen to need to repeat lists of
    strings (which are immutable), but that's not what i asked about now
    is it. :)

    --
    Regards
    André Risnes
     
    alr, Jul 2, 2003
    #13
    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. Andy B.
    Replies:
    2
    Views:
    712
    Andy B.
    Feb 19, 2009
  2. Ben Cohen
    Replies:
    4
    Views:
    1,238
    Jean-Michel Pichavant
    May 10, 2010
  3. John Lam
    Replies:
    4
    Views:
    276
  4. Jay Levitt
    Replies:
    19
    Views:
    254
    Steve Austen
    Nov 29, 2010
  5. Kendall Gifford
    Replies:
    18
    Views:
    276
    paron
    Jun 12, 2009
Loading...

Share This Page