このタイトルが良いかどうかわかりません。誰かがそれを変更するのを助けてくれることを願っています。2つ以上の同時反復をサポートする反復可能なクラスを定義する
私はmolecule
クラスを定義しようとしています。その原子を反復できることを願っています。 私は人々が反復可能なクラスを定義する方法を探索し、それは次のようになります。それがうまく機能
class molecule(object):
def __init__(self,name):
self.__pointer=0
# ...something else
def __iter__(self):
self.__pointer=0
return self
def __next__(self):
self.__pointer+=1
if self.__pointer<=self.natoms: # self.natoms is defined somewhere
return self[self.__pointer] # suppose __getitem__ is defined to return an atom object
else:
raise StopIteration("Exceeded all atoms")
:
>>> ben=molecule('ben') #defined a molecule
>>> ben.addatom(...) # and defined some atoms
>>> ite=iter(ben)
>>> for atom in ite:
... print(atom)
...
# atom objects are correctly printed here
をしかし、私は彼らが同時に存在する場合、それは、2回の反復子では動作しないことができました。 2回の反復子がそうゼロへのポインタを更新する新しいイテレータを定義し、同じself.__pointer
を共有するため
>>> ite=iter(ben)
>>> next(ite)
# atom1
>>> next(ite)
# atom2
>>> ite2=iter(ben)
>>> next(ite)
# atom1 again, where atom3 is expected
>>> next(ite2)
# atom2, where atom1 is expected
これは驚きではありません。
私はこのページを見ていて、ほとんどの人がクラス内でself.__pointer
を使用しています。これが私の質問を呼び起こします。 pointer
が反復子(ite
またはite2
)の属性であり、反復されたオブジェクト自体(molecule
)の属性ではないと思われる場合、この問題は解決できます。
誰かがいくつかの助けを与えることを望む:)ありがとう。
>:
DEMO:
__iter__()
は新しいジェネレータイテレータを返しますので。 <<どのようにする? 'yield'を使うのがよさそうです。 –@RuixingWang、最初のオプションのコードを含めるように答えを更新しました。 (新しいイテレータインスタンスを返す) – falsetru
クールな答え。コメント '#Are you sure'、はい、私は1から原子を数えますが、ゼロではありません:)ありがとう! –