3

分散キャッシュ製品とは、CoherenceやHazelcastのようなものを意味します。例としてHazelcastを使用します。

いくつかのマップで状態を保持するオブジェクトがあるとします。

class DataState {
    Map<ID, Dog> dogs = Hazelcast.getMap("dog");
    Map<ID, Owner> owners = Hazelcast.getMap("owner");

    public void associate(Dog dog, Owner owner) { 
          /* ... put in maps and set up references */ 
    }
}

アソシエート()関数は複数のマップを変更するため、トランザクションである必要があることに注意してください。犬と飼い主は何らかの形で関連付けられているため、メソッドが完了するまでデータが一貫性のない状態になっている可能性があります。これで、別のクラスが分散メモリから読み取る場合、トランザクションが発生していることを認識できず、データの表示に一貫性がなくなる可能性があります。

class DataStateClient {
     Map<ID, Dog> dogs = Hazelcast.getMap("dog");
     Map<ID, Owner> owners = Hazelcast.getMap("owner");

     public void doSomething() {
        // oops, owner2 is associated with dog1 but
        // dog1 is not yet in the map!
    }
}

現在、Hazelcastはこのような問題を解決するためにロックを分散していますが、パフォーマンスへの影響は何ですか?doSomething()が高価であると仮定します(たとえば、両方のマップをローカルにコピーする)。その場合、複数のクライアントをロックアウトするのは適切でない可能性があります。

この分散同期の問題に対する標準的な解決策はありますか?

4

1 に答える 1

1

書き込みアクセス(相互排除)をシリアル化する場合は、分散ロックが最適です。Cacheonixを使用している場合、Cacheonixの読み取り/書き込みロックを使用すると、例のパフォーマンスが向上する可能性があります。このようにして、リーダーは同時読み取りアクセスを持ち、単一のサーバーが終了するのを待つ必要がなくなります。これは、単純なミューテックスが使用された場合のケースです。

ライター:

  final Cacheonix cacheonix = Cacheonix.getInstance();
  final ReadWriteLock rwLock = cacheonix.getCluster().getReadWriteLock();
  final Lock writeLock = rwLock.writeLock();
  writeLock.lock();
  try {
     // No one else can enter this section

     // Update dogs

     // Update owners
  } finally {
     writeLock.unlock();
  }

..。

読者:

  final Cacheonix cacheonix = Cacheonix.getInstance();
  final ReadWriteLock rwLock = cacheonix.getCluster().getReadWriteLock();
  final Lock readLock = rwLock.readLock();
  readLock.lock();
  try {
     // Readers can enter this section simultaneously 

     // Read dogs

     // Read owners
  } finally {
     readLock.unlock();
  }
于 2011-09-20T02:56:19.147 に答える