4

getメソッドにアクセスする多くのスレッドとsetListメソッドにアクセスするスレッドが1つだけの場合、これを同期する必要がありますか?

public class ListContainer {
  private List<String> myList = new ArrayList<String();

  public List<String> get ( )
  {
    return new ArrayList<String>(myList);
  }

  public List<String> set ( )
  {
    this.myList = computeList();
  }
}

読者が古いデータを取得してもかまいませんが、データは一貫している必要があります。

ジャニング

4

4 に答える 4

5

次の条件が true の場合、同期する必要はありません (ただし、myListとして宣言する必要があります)。volatile

  • computeListの現在の状態に依存しないmyList
  • 割り当てられた後にリストの内容を変更しない (Collections.unmodifiableList(computeList())この条件を表現するより良い方法です)
于 2010-02-22T16:52:16.803 に答える
1

いいえ、同期は必要ありません。同時変更はありません (computeList()に依存しない場合myList)。

new ArrayList(myList)ところで、単に return ではなく、なぜ戻ってくるのmyListですか?

于 2010-02-22T16:54:44.603 に答える
0

私はむしろ暗黙のコピーをしたい

public class ListContainer {

    private final List<String> myList = new CopyOnWriteArrayList<String>();

    public List<String> get (){
      return myList;
    }

    public List<String> set (){
       computeList();
    }
}

HTH

于 2010-02-24T00:35:07.083 に答える
0

computeList が myList に依存するかどうかは問題ではなく、myList のコンテンツへの読み取りアクセスのみが存在する限り、同期の問題は発生しません。

myList に volatile を使用しない場合、厳密に set がリストを既に置き換えていても、get が古い myList を返すことが発生する可能性があります。この状況が気にならない場合 (2 つのスレッドが異なる値を参照する可能性がある場合)、volatile は必要ありません。

于 2010-02-22T17:45:29.460 に答える