2

有効ですか?つまり、連絡先内でIterator、前の反復と同じ(可変)オブジェクトを返すか、前のオブジェクトとして可変状態を共有する新しいオブジェクトを返すか。つまり、next()文書化されている限り、前の呼び出しによって返されたオブジェクトを無効にするために1つの呼び出しを行うことができますか?

私はこれが一般的に良い考えではないことを完全によく理解しています、そして私はそれを習慣にしません。

ただし、同じ基になるオブジェクト、または内部が共有されている新しいオブジェクト(したがって、以前に返されたオブジェクトの内部を無効にする可能性があります)を再利用すると、重要で測定可能な場合があります。良い例は、イテレータから返されたオブジェクトが、オフセットと長さを持って、を含むバッファ配列に保持されているIterable場合です。この配列は、後続のオブジェクトが取得されるときに上書きされる可能性があります。

確かに、これは驚き最小の原則に違反しており、クライアントに不親切かもしれませんが、それが連絡先に違反しているかどうか知りたいのですが、それIteratorを文書化する限り、私はルールの範囲内で遊んでいますか?

javadocはコレクションに焦点を当てて作成されているようです。呼び出し間で状態を共有することnext()はおそらく無意味ですIteratorが、汎用インターフェースです(バッキングコレクションなしで、またはバッキングなしでも実装できます

基本的に、私はフライウェイトパターンに匹敵する、パフォーマンスの面で何かを実装しようとしていますが、Javaイテレータの優れた点を維持しています。

このパターンに従うイテレータは、次のように安全に使用できます。

for (Foo foo : FooIterable) {
  if (foo.method()) {
    System.println("ha!");
  }
}

の各インスタンスはfoo、ある反復から別の反復にエスケープすることはありません。ただし、次のようなものは一般的には機能しません。

List<Foo> allTheFoos = ...;
for (Foo foo : FooIterable) {
  allTheFoos.add(foo);
}

for (Foo foo : allTheFoos) {
  ...
}

最初のループのfoosは格納されているため、反復を回避できます。後でそれらにアクセスすると、それらの状態が無効になる可能性があります(たとえば、foo最初の反復から最後に返されたように見える場合があります。

4

1 に答える 1

0

AListには同じオブジェクトを複数含めることができIterator、リスト内で出現するこのオブジェクトを返します。したがって、これはおそらく契約で禁止されているものではありません。ASetに重複を含めてはならないため、同じオブジェクトを 2 回返すことはありません。

コレクションはメンバーを変更したり無効にしたりすることはありませんが、イテレーター自体の内部には状況に似たものがあります。コレクションが変更されている場合、無効になります (呼び出し時に例外がスローされます)。これは、返されたオブジェクトが無効になった場合の解決策のヒントになる可能性があります。

おそらく、あなたの反復は、その変化するオブジェクトに関するラッパーを返し、以前に返された無効なラッパーのすべての呼び出しが例外をスローするようにすることができます。

于 2013-01-17T07:32:51.280 に答える