web-dev-qa-db-ja.com

Python range()and Zip()object type

range()Zip()などの関数をforループで使用する方法を理解しています。しかし、range()がリストを出力することを期待していました-UNIXシェルのseqによく似ています。次のコードを実行すると:

_a=range(10)
print(a)
_

出力はrange(10)であり、リストではなく、異なるタイプのオブジェクトを示唆しています。 Zip()は、印刷時に同様の動作をし、次のようなものを出力します

_<Zip object at "hexadecimal number">
_

だから私の質問は、それらが何であり、これを作ることにはどのような利点があるのか​​、そしてそれらをループすることなくリストに出力を得るにはどうすればよいですか?

47
Michal

Python 3。

Python 2)では、オブジェクトZipおよびrangeは、リストを返すように、提案どおりに動作しました。これらは generator に変更されましたリスト全体をメモリに展開するのではなく、要求に応じて要素を生成する-オブジェクトのようなもの。

「遅延」バージョンもPython 2.xにありますが、xrangeitertools.izip

一度にすべての出力を使い慣れたリストオブジェクトに取得するには、単にlistを呼び出して、コンテンツを繰り返し使用します。

>>> list(range(3))
[0, 1, 2]
>>> list(Zip(range(3), 'abc'))
[(0, 'a'), (1, 'b'), (2, 'c')]
76
wim

In Python 3.x.、 range は、Python = 2.x.同様に、 Zip はリストではなくZipオブジェクトを返すようになりました。

これらのオブジェクトをリストとして取得するには、それらを list に配置します。

>>> range(10)
range(0, 10)
>>> list(range(10))
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
>>> Zip('abc', 'abc')
<Zip object at 0x01DB7120>
>>> list(Zip('abc', 'abc'))
[('a', 'a'), ('b', 'b'), ('c', 'c')]
>>>

最初は役に立たないように思えるかもしれませんが、rangeZipの動作のこの変更により、実際に効率が向上します。これは、Zipオブジェクトとrangeオブジェクトが、一度にすべてを保持するリストを作成するのではなく、必要に応じてアイテムを作成するためです。そうすることで、メモリ消費を節約し、操作速度を改善します。

20
iCodez

範囲(xrange in python 2. *)オブジェクトは 不変シーケンス で、Zip(itertools.izipは、それぞれ) ジェネレーターオブジェクト です。ジェネレーターまたはシーケンスからリストを作成するには、単純にリストにキャストします。例えば:

>>> x = range(10) 
>>> list(x)
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]

ただし、要素の生成方法は異なります。通常のジェネレーターは可変であり、反復されるとその内容を検証しますが、範囲は不変であり、次のことは行いません。

>>> list(x) # x is a range-object
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9] # second cast to list, contents is the same
>>> y = Zip('abc', 'abc')
>>> list(y) # y is a generator
[('a', 'a'), ('b', 'b'), ('c', 'c')]
>>> list(y) 
[] # second cast to list, content is empty!
3
alko