tags:

views:

212

answers:

9

I am using Python 2.5, I want an enumeration like so (starting at 1 instead of 0):

[(1, 2000), (2, 2001), (3, 2002), (4, 2003), (5, 2004)]

I know in Python 2.6 you can do: h = enumerate(range(2000, 2005), 1) to give the above result but in python2.5 you cannot...

Using python2.5:

>>> h = enumerate(range(2000, 2005))
>>> [x for x in h]
[(0, 2000), (1, 2001), (2, 2002), (3, 2003), (4, 2004)]

Does anyone know a way to get that desired result in python 2.5?

Thanks,

Jeff

A: 

h = [(i + 1, x) for i, x in enumerate(xrange(2000, 2005))]

Chris B.
+1 for the oneliner
Randolpho
He can't do this in Python 2.5. The start parameter was introduced in Python 2.6: http://docs.python.org/library/functions.html#enumerate. He also mentions this in the question.
Mark Byers
way to read the entire question...
Wallacoloo
Answered this before the initial edit, when the code was unformatted and the trouble seemed to me to be the use of a generator instead of a list.
Chris B.
`++`: that's the way to do it
Nas Banov
Wow thanks for the magnitude of options guys.
JeffTaggary
+13  A: 

You could create two range objects and zip them:

r = xrange(2000, 2005)
h = zip(xrange(1, len(r) + 1), r)
print h

Result:

[(1, 2000), (2, 2001), (3, 2002), (4, 2003), (5, 2004)]

If you want to create a generator instead of a list then you can use izip instead.

Mark Byers
+1 for clean and simple and readable.
zdav
using `izip` and `xrange` would be closer to enumerate
gnibbler
Very clean, love it, thanks.
JeffTaggary
A: 
>>> h = enumerate(range(2000, 2005))
>>> [(tup[0]+1, tup[1]) for tup in h]
[(1, 2000), (2, 2001), (3, 2002), (4, 2003), (5, 2004)]

Since this is somewhat verbose, I'd recommend writing your own function to generalize it:

def enumerate_at(xs, start):
    return ((tup[0]+start, tup[1]) for tup in enumerate(xs))
Eli Courtwright
enumerate should be a generator. creating a whole list at once just to iterate over if often not acceptable
gnibbler
`start` is unused :(
John Machin
+3  A: 
from itertools import count, izip

def enumerate(L, n=0):
    return izip( count(n), L)

# if 2.5 has no count
def count(n=0):
    while True:
        yield n
        n+=1

Now h = list(enumerate(xrange(2000, 2005), 1)) works.

THC4k
2.5 does have `count()`
gnibbler
+4  A: 

Easy, just define your own function that does what you want:

def enum(seq, start=0):
    for i, x in enumerate(seq):
        yield i+start, x
Duncan
+2  A: 
delnan
Your second solution gives a syntax error.
Philipp
Yep, total nonsense. Something along these lines would actually work in e.g. Haskell (currying is the most natural thing ever in that language, and due to its laziness, a function taking a list is very similar to a generator expressiong). But that doesn't excuse me - long-time python user - writing BS. Thanks for pointing it out.
delnan
+2  A: 
>>> list(enumerate(range(1999, 2005)))[1:]
[(1, 2000), (2, 2001), (3, 2002), (4, 2003), (5, 2004)]
JAB
enumerate should be a generator. creating a whole list at once just to iterate over if often not acceptable
gnibbler
Generalized:start=4list(enumerate(range(start)+range(1999, 2005)))[start:]
Tony Veijalainen
range is however list in 2.52
Tony Veijalainen
+4  A: 

Simplest way to do in Python 2.5 exactly what you ask about:

import itertools as it

... it.izip(it.count(1), xrange(2000, 2005)) ...

If you want a list, as you appear to, use zip in lieu of it.izip.

(BTW, as a general rule, the best way to make a list out of a generator or any other iterable X is not [x for x in X], but rather list(X)).

Alex Martelli
A: 

Ok, I feel a bit stupid here... what's the reason not to just do it with something like
[(a+1,b) for (a,b) in enumerate(r)] ? If you won't function, no problem either:

>>> r = range(2000, 2005)
>>> [(a+1,b) for (a,b) in enumerate(r)]
[(1, 2000), (2, 2001), (3, 2002), (4, 2003), (5, 2004)]

>>> enumerate1 = lambda r:((a+1,b) for (a,b) in enumerate(r)) 

>>> list(enumerate1(range(2000,2005)))   # note - generator just like original enumerate()
[(1, 2000), (2, 2001), (3, 2002), (4, 2003), (5, 2004)]
Nas Banov