回答:
いいえ、そのような方法はありません。反復の終了は例外によって示されます。ドキュメントを参照してください。
unnext()
呼び出して最初の要素が存在することを確認した後、最初の要素を元に戻すメソッドがあった場合、try catchソリューションを受け入れますnext()
。
yield
ません)。の結果を格納するアダプター書くために、もちろん、難しいことではないnext()
と提供has_next()
とをmove_next()
。
hasNext()
メソッドを実装することもできます(成功した場合はtrueを生成、キャッシュしてtrueを返し、失敗した場合はfalseを返します)。そして、両方hasNext()
とnext()
共通基盤となるに依存するgetNext()
方法と、キャッシュされたアイテム。next()
それを提供するアダプターを実装するのがとても簡単なのに、なぜ標準ライブラリに入れるべきではないのか本当にわかりません。
next()
とhasNext()
メソッドに影響します)。そうです、next()
そしてhasNext()
スキャンされたストリームの内容がに依存する場合、トリッキーになったときに要素が読み込まれます。
StopIteration
を使用することで、に代わるものがありnext(iterator, default_value)
ます。
例:
>>> a = iter('hi')
>>> print next(a, None)
h
>>> print next(a, None)
i
>>> print next(a, None)
None
そのためNone
、例外の方法が必要ない場合は、イテレータの終了を検出するか、イテレータの最後に他の事前に指定された値を指定できます。
sentinel = object()
、next(iterator, sentinel)
を使用してテストすることもできますis
。
unittest.mock.sentinel
ますが、明示的に記述することができますオブジェクトnext(a, sentinel.END_OF_ITERATION)
、その後if next(...) == sentinel.END_OF_ITERATION
本当に機能が必要なhas-next
場合(たとえば、Javaの参照実装からアルゴリズムを忠実に転記しているため、または、完成したときにJavaに簡単に転記する必要があるプロトタイプを作成しているため)、それは簡単です小さなラッパークラスで取得します。例えば:
class hn_wrapper(object):
def __init__(self, it):
self.it = iter(it)
self._hasnext = None
def __iter__(self): return self
def next(self):
if self._hasnext:
result = self._thenext
else:
result = next(self.it)
self._hasnext = None
return result
def hasnext(self):
if self._hasnext is None:
try: self._thenext = next(self.it)
except StopIteration: self._hasnext = False
else: self._hasnext = True
return self._hasnext
今のようなもの
x = hn_wrapper('ciao')
while x.hasnext(): print next(x)
発する
c
i
a
o
要求に応じ。
をnext(sel.it)
組み込みとして使用するには、Python 2.6以降が必要です。古いバージョンのPythonを使用している場合は、self.it.next()
代わりに使用します(next(x)
使用例でも同様です)。[[Python 2.6が1年以上前から存在しているため、このメモは冗長であると合理的に考えるかもしれませんが、Python 2.6の機能を応答で使用する場合は、多くの場合、一部のコメンターまたは他の人が指摘する義務があると感じていますそれらは 2.6の機能であるため、そのようなコメントを1度は未然に防ぐようにしています;-)]]
has_next
メソッドを必要とする最悪の理由です。Pythonの設計では、たとえば、filter
指定された述語に一致する要素が配列に含まれているかどうかをチェックすることはできません。Pythonコミュニティの傲慢さと近視眼は驚異的です。
TypeError: iter() returned non-iterator
map
、のany
代わりにおよびを使用しfilter
ますが、を使用SENTINEL = object(); next(filter(predicate, arr), SENTINEL) is not SENTINEL
または忘れてSENTINEL
、を使用try: except
してキャッチすることもできますStopIteration
。
StopIterationに関するすべての言及に加えて、Pythonの「for」ループは単純にあなたが望むことをします:
>>> it = iter("hello")
>>> for i in it:
... print i
...
h
e
l
l
o
イテレータオブジェクトから__length_hint __()メソッドを試してください。
iter(...).__length_hint__() > 0
__init__
して __main__
?Imho、それを正当化しようとするかどうかに関係なく、少し混乱しています。
hasNext
ややStopIteration
例外に変換されます。例:
>>> it = iter("hello")
>>> it.next()
'h'
>>> it.next()
'e'
>>> it.next()
'l'
>>> it.next()
'l'
>>> it.next()
'o'
>>> it.next()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
StopIteration
StopIteration
docs:http : //docs.python.org/library/exceptions.html#exceptions.StopIterationいいえ。最も類似した概念は、StopIteration例外です。
私はpythonにnext()しかないと信じており、ドキュメントによると、要素がなくなった場合に例外がスローされます。
これを検索するようになったユースケースは次のとおりです
def setfrom(self,f):
"""Set from iterable f"""
fi = iter(f)
for i in range(self.n):
try:
x = next(fi)
except StopIteration:
fi = iter(f)
x = next(fi)
self.a[i] = x
hasnext()が利用可能な場合、
def setfrom(self,f):
"""Set from iterable f"""
fi = iter(f)
for i in range(self.n):
if not hasnext(fi):
fi = iter(f) # restart
self.a[i] = next(fi)
私にはどちらがきれいですか。明らかに、ユーティリティクラスを定義することで問題を回避できますが、その後発生するのは、それぞれに癖がある20種類のほぼ同等の回避策が急増していることです。異なる回避策を使用するコードを再利用する場合は、次のいずれかを行う必要があります。単一のアプリケーションに同等のものが複数ある場合、または同じアプローチを使用するようにコードを選択して書き直す場合。「一度やればうまくいく」という格言はひどく失敗する。
さらに、イテレーター自体は、例外を発生させる必要があるかどうかを確認するために実行する内部の「hasnext」チェックが必要です。その後、この内部チェックは非表示になるため、アイテムを取得して例外をキャッチし、スローされた場合はハンドラーを実行してテストする必要があります。これはIMOを非表示にする必要はありません。
推奨される方法はStopIterationです。チュートリアルポイントからフィボナッチの例をご覧ください
#!usr/bin/python3
import sys
def fibonacci(n): #generator function
a, b, counter = 0, 1, 0
while True:
if (counter > n):
return
yield a
a, b = b, a + b
counter += 1
f = fibonacci(5) #f is iterator object
while True:
try:
print (next(f), end=" ")
except StopIteration:
sys.exit()
私が問題を解決した方法は、これまでに繰り返されたオブジェクトの数を数えることです。インスタンスメソッドの呼び出しを使用してセットを反復処理したかったのです。セットの長さと、これまでにカウントされたアイテムの数がわかっているので、効果的なhasNext
方法がありました。
私のコードの簡単なバージョン:
class Iterator:
# s is a string, say
def __init__(self, s):
self.s = set(list(s))
self.done = False
self.iter = iter(s)
self.charCount = 0
def next(self):
if self.done:
return None
self.char = next(self.iter)
self.charCount += 1
self.done = (self.charCount < len(self.s))
return self.char
def hasMore(self):
return not self.done
もちろん、この例はおもちゃですが、あなたはそのアイデアを理解しました。これは、ジェネレータなど、イテラブルの長さを取得する方法がない場合には機能しません。