1から始まる数値の範囲を列挙する方法


154

私はPython 2.5を使用しています。そのような列挙が必要です(0ではなく1から開始):

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

私はPython 2.6であなたができることを知っています:h = enumerate(range(2000、2005)、1)上記の結果を与えるが、python2.5ではできません...

python2.5を使用:

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

誰もがPython 2.5でその望ましい結果を得る方法を知っていますか?

おかげで、

ジェフ


4
私がPythonのやり方を専門的に行ったことのない人なので、興味があるだけです。互換性の理由でアップグレードを望まないため、Python 2.5に限定されていますか?
Sean、

2
すべての2.xバージョンは下位互換性があるため、理由はありません。
Jochen Ritzel、2010

一部のモジュールにそれを伝えて
ください-Py

回答:


179

すでに述べたように、これはPython 2.6以降で簡単に実行できます。

enumerate(range(2000, 2005), 1)

Python 2.5以前はstartパラメータをサポートしていないため、代わりに2つの範囲オブジェクトを作成してそれらを圧縮できます。

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

結果:

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

リストの代わりにジェネレータを作成したい場合は、代わりにizipを使用できます。


使用izipxrangeて列挙するのに近い
John La Rooy 2010

7
この答えは時代遅れであり、enumerate(iterable, start=1)Python 2.6と同じように置くことができます。
Fredrick Brennan

@frb:質問を読みましたか?彼はすでにPython 2.6のソリューションを知っています。彼は特にPython 2.5で動作するソリューションを求めました。
マーク・バイアーズ2013

1
@MarkByersどうやら私は盲目です:)本当に申し訳ありません。(これは、「1から始まる列挙」のGoogleナンバー1です)
Fredrick Brennan

2
@ 8chanはい、私はグーグル検索からここに来たばかりです "ゼロパイソンから列挙を開始します" :)
baxx

166

後世のためにこれをここに置くために、2.6では "start"パラメータが次のように列挙するために追加されました。

enumerate(sequence, start=1)


26
これはリストの最初の項目をスキップしないことに注意してください。開始値によってインデックスをオフセットするためsequence[i]、コード内で次のようなことをすると、配列が範囲外になります。
phyatt

14

簡単です。必要なことを行う独自の関数を定義するだけです。

def enum(seq, start=0):
    for i, x in enumerate(seq):
        yield i+start, x

12

Python 3

公式ドキュメント: enumerate(iterable, start=0)

したがって、次のように使用します。

>>> seasons = ['Spring', 'Summer', 'Fall', 'Winter']

>>> list(enumerate(seasons))
[(0, 'Spring'), (1, 'Summer'), (2, 'Fall'), (3, 'Winter')]

>>> list(enumerate(seasons, start=1))
[(1, 'Spring'), (2, 'Summer'), (3, 'Fall'), (4, 'Winter')]

10

あなたが尋ねたとおりに正確にPython 2.5で行う最も簡単な方法:

import itertools as it

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

リストが必要な場合は、見かけのとおり、のzip代わりに使用してくださいit.izip

(ところで、原則として、ジェネレーターやその他の反復可能なXからリストを作成する最良の方法 [x for x in X]、ではなくですlist(X))。


6
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

今はh = list(enumerate(xrange(2000, 2005), 1))動作します。


6

enumerateは取るに足らないことなので、開始を受け入れるように再実装します。

def enumerate(iterable, start = 0):
    n = start
    for i in iterable:
        yield n, i
        n += 1

これは、開始引数なしで列挙を使用してコードを壊さないことに注意してください。または、このonelinerはよりエレガントでおそらく高速かもしれませんが、列挙の他の使用法を壊します:

enumerate = ((index+1, item) for index, item)

後者はまったくナンセンスでした。@Duncanはラッパーを正しく設定しました。


うん、まったくナンセンス。これらの線に沿ったものは実際にHaskellなどで実際に機能します(カレーはその言語ではこれまでで最も自然なものであり、その遅延のために、リストを取得する関数はジェネレータ式に非常に似ています)。しかし、それは私を許しません-長いPythonユーザー-BSを書く。指摘してくれてありがとう。

5
>>> list(enumerate(range(1999, 2005)))[1:]
[(1, 2000), (2, 2001), (3, 2002), (4, 2003), (5, 2004)]

enumerateはジェネレータでなければなりません。多くの場合受け入れられない場合に反復するために、一度にリスト全体を作成します
John La Rooy 2010

一般化:start = 4 list(enumerate(range(start)+ range(1999、2005)))[start:]
Tony Veijalainen

ただし、範囲は2.52にリストされています
Tony Veijalainen

3

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


1
彼はPython 2.5ではこれを行うことができません。startパラメータはPython 2.6で導入されました:docs.python.org/library/functions.html#enumerate。彼はこれについても質問の中で述べています。
Mark Byers、2010

最初の編集の前にこれに答えました。コードがフォーマットされておらず、問題はリストではなくジェネレータを使用しているように思えました。
Chris B.

++:それがその方法です
Nas Banov

2

さて、ここで少しバカな感じがします...そんなことをやらない理由は何
[(a+1,b) for (a,b) in enumerate(r)]ですか?機能しない場合も問題ありません。

>>> 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)]

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

これはやや冗長なので、一般化するために独自の関数を書くことをお勧めします。

def enumerate_at(xs, start):
    return ((tup[0]+start, tup[1]) for tup in enumerate(xs))

2
enumerateはジェネレータでなければなりません。多くの場合許容できない場合は単に繰り返すために、一度にリスト全体を作成します
John La Rooy 2010

0

これらの投稿が次の方法よりも複雑になる可能性がある方法はわかりません。

# Just pass the start argument to enumerate ...
for i,word in enumerate(allWords, 1):
    word2idx[word]=i
    idx2word[i]=word
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.