ホームページ  >  記事  >  バックエンド開発  >  Python の range オブジェクトがイテレータであるかどうかについての議論

Python の range オブジェクトがイテレータであるかどうかについての議論

零到壹度
零到壹度オリジナル
2018-04-02 14:28:452598ブラウズ

Iterator (反復子) は、Python 3 の遅延反復可能オブジェクト (lazy iterable) です。 では、range は反復子ですか?なぜ。

TLNR: Python 3 の Range オブジェクト (Python 2 の xrange オブジェクト) は遅延型ですが、Range オブジェクトはイテレーターではありません。はい、それは混乱しています。Pythonで反復因子と反復について話すとき、あなたはおそらく、範囲がイテレーターであるという誤解を繰り返すのを聞くでしょう。これは非常に重大な誤解だと思います。範囲オブジェクトがイテレータであると考えている場合、「イテレータがどのように機能するか」というメンタル モデルが十分に明確ではありません。ある意味、範囲とイテレータはどちらも「怠惰」ですが、まったく異なる方法で「怠惰」を実現します。


イテレーターとは何ですか?

Python では、反復可能オブジェクトとは反復可能なオブジェクトのことであり、イテレーターとは実際に反復処理を行うものです。

Iter-

ables

は反復可能です


イテレータを取得したら、それに対してできることは次の要素を取得することだけです:

要素がもうない場合、反復停止例外:

すべての反復子は反復可能オブジェクトです。つまり、反復子から反復子を取得できるため、反復子を反復処理できます:

Python の range オブジェクトがイテレータであるかどうかについての議論

イテレータはステートフルであることに注意してください。一度ループした後、再度ループしようとすると空になります:

Python の range オブジェクトがイテレータであるかどうかについての議論

Python 3 では、<code style="box-sizing: inherit;margin-right: 2px;margin-left: 2px;padding: 3px 4px;border-radius: 3px;"><span style="color: rgb(103, 103, 103);">enumerate、zip、reversed</span>列挙、zip、反転

およびその他のビルド-in 関数はイテレータを返します:

Python の range オブジェクトがイテレータであるかどうかについての議論

ジェネレータ (ジェネレータ関数またはジェネレータ式のいずれかから) は、イテレータを作成する簡単な方法です:

Python の range オブジェクトがイテレータであるかどうかについての議論

イテレータは怠惰なものであるとよく言います。 -time 反復可能オブジェクト。 「遅延」はループ内の項目のみをカウントするため、「使い捨て」は要素がイテレーターから「消費」されると、その要素は永久に失われるためです。


Rangetpython 3 の Range オブジェクト (Python 2 の XRANGE) は、他の反復オブジェクトと同様に強化オブジェクトとして使用できます:

, したがって、そこからイテレータを取得できます:

Python の range オブジェクトがイテレータであるかどうかについての議論

しかし、範囲オブジェクト自体はイテレータではないため、範囲オブジェクトに対して next を呼び出すことはできません:

Python の range オブジェクトがイテレータであるかどうかについての議論

イテレータとは異なり、範囲オブジェクトを「消費」せずに反復できます:

Python の range オブジェクトがイテレータであるかどうかについての議論

イテレータでこれを実行すると、2回目は何も取得されませんループ時の要素:

Python の range オブジェクトがイテレータであるかどうかについての議論

Zongshang、<code style="box-sizing: inherit;margin-right: 2px;margin-left: 2px;padding: 3px 4px;border-radius: 3px;"><span style="color: rgb(103, 103, 103);">zip</span><span style="color: rgb(103, 103, 103);">enumerate</span>, or <span style="color: rgb(103, 103, 103);">generator</span>zip,

<p style="box-sizing: inherit;margin-bottom: 20px;color: rgb(51, 51, 51);margin-left: 8px;margin-right: 8px;line-height: 1.75em;">列挙<span style="box-sizing: inherit;font-weight: 600;color: rgb(103, 103, 103);font-size: 20px;"></span></p>
、または generator<p style="box-sizing: inherit;margin-bottom: 20px;color: rgb(51, 51, 51);margin-left: 8px;margin-right: 8px;line-height: 1.75em;"> </p> オブジェクトが異なります。範囲オブジェクトはイテレータではありません。

では、範囲とは正確には何でしょうか?

Python の range オブジェクトがイテレータであるかどうかについての議論 range オブジェクトは、作成時に含まれるすべての数値を生成するのではなく、作成時に生成するという意味で「遅延」します。ループ内で必要な場合にのみ、これらの数値を返します。

ここに範囲オブジェクトとジェネレーター (反復子) があります:

Python の range オブジェクトがイテレータであるかどうかについての議論

ジェネレーターとは異なり、範囲オブジェクトには長さがあります:

🎜🎜🎜🎜🎜🎜🎜 : 🎜🎜

Python の range オブジェクトがイテレータであるかどうかについての議論

イテレータとは異なり、状態を変更せずに要素が含まれているかどうかを尋ねることができます:

Python の range オブジェクトがイテレータであるかどうかについての議論

範囲オブジェクトの説明が必要な場合は、それらを呼び出すことができます <code style="box-sizing: inherit;margin-right: 2px;margin-left: 2px;padding: 3px 4px;border-radius: 3px;"><span style="color: rgb(103, 103, 103);">懒序列</span>遅延シーケンス、範囲はシーケンス (たとえば、リスト、タプル、文字列など)を含みますが、メモリ内のコンテンツは含まれていませんが、代わりに計算を実行して質問に答えます。

Python の range オブジェクトがイテレータであるかどうかについての議論


この違いが重要な理由

オブジェクトがイテレータであることを説明すると、このオブジェクトに対して iter 関数が呼び出されるときに、 (定義により) 常に同じオブジェクトを取得します:

Python の range オブジェクトがイテレータであるかどうかについての議論

次の関数はすべての反復子で呼び出すことができるため、このオブジェクトで次の関数を呼び出せることを確認してください:

Python の range オブジェクトがイテレータであるかどうかについての議論

そして、それを反復処理すると、これらの要素がイテレータから消費されることがわかりますが、この機能が (特別な方法でイテレータを処理するために) 役立つ場合があります:

Python の range オブジェクトがイテレータであるかどうかについての議論

「遅延反復可能オブジェクト」と「反復子」の違いは微妙なように思えるかもしれませんが、これらの用語は意味が異なります。 「遅延反復可能オブジェクト」は非常に一般的な用語であり、特別な意味はありませんが、「反復子」という言葉は、非常に特殊な動作を持つオブジェクトを意味します。

🎜


概要

オブジェクトをループできることがわかっている場合、それは反復可能なオブジェクト (iterable) です。

ループしているオブジェクトがループ中に計算されることがわかっている場合、それは遅延反復可能 (lazy iterable) です。

次の関数に何かを渡すことができることがわかっている場合、それはイテレーター (最も一般的な遅延反復可能オブジェクト) です。

「使い果たす」ことなく複数回ループできる場合、それはイテレータではありません。次の関数に何かを渡せない場合、それはイテレータではありません。 Python 3 の range オブジェクトはイテレータではありません。 範囲オブジェクトについて他の人に指示する場合は、「イテレータ」という言葉を使用しないでください。これは非常に混乱を招くため、他の人が「イテレータ」という言葉を乱用する可能性があります

関連する推奨事項:

イテレータの詳しい説明

Pythonの反復可能オブジェクトとイテレータオブジェクトの理解

Rangeオブジェクト

以上がPython の range オブジェクトがイテレータであるかどうかについての議論の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。