1

を使用するReaderWriterLock場合は、次のように宣言します。

ReaderWriterLock rwLock = new ReaderWriterLock;

保護したいリソースにアクセスしようとしているすべての異なるスレッドに対してこれを行っている場合、それらはすべて(おそらく)異なるReaderWriterLockインスタンスを使用しています。

ReaderWriterLockインスタンスはスレッド間でどのように共有されますか?

また、ボーナスとして、あなたが本当に「ロック」しているのはReaderWriterLock状態であり、リソースではないことを誰かが確認できますか。とは異なりlock(someResourceToLock)、ReaderWriterLockインスタンスの状態(読み取りモードか書き込みモードか、および読み取りと書き込みがまだ許可されているかどうか)以外はロックしていません。

4

2 に答える 2

2

ReaderWriterLockインスタンスはスレッド間でどのように共有されますか?

の単一インスタンスを作成し、ReaderWriterLock保護する共有リソースにアクセスしているすべてのスレッドからそれを使用します。

また、ボーナスとして、あなたが本当に「ロック」しているのはReaderWriterLock状態であり、リソースではないことを誰かが確認できますか。lock(someResourceToLock)とは異なり、ReaderWriterLockインスタンスの状態以外はロックしていません。

あなたは本当にロックしています。

lock(obj) { ... }は単なるショートカットです(ここでは簡略化されていますが、実際の実装には、エッジケースを処理するためのいくつかの追加の微妙な点があります):

Monitor.Enter(obj)
  ...
try {
} finally {
  Monitor.Exit(obj);
}

すべての参照型のフィールドを使用して、によって使用される状態を保持しMonitorます。


マークが指摘しているようにReaderWriterLockSlim、公平性(待機を開始する順序でスレッドが入ることが保証されている)が必要でない限り、検討してくださいReaderWriterLock

于 2011-04-20T07:06:38.570 に答える
2

ReaderWriterLock rwLock = new ReaderWriterLock スレッドごとまたはメソッドごと(つまり、メソッド変数として)を使用している場合、コードが壊れている可能性が高くなります。シングルトンではありません。同じロックを使用して保護されたデータにアクセスするすべてのスレッドに依存します。これは、フィールドにロックを配置することによって最も一般的に達成されます。

class Foo {
    ReaderWriterLock rwLock = new ReaderWriterLock();
    // lots of code accessing the rwLock field for this instance
}

ReaderWriterLockSlimまた、多くのシナリオで検討してください。オーバーヘッドが少ない。フォローアップを再確認してください。ロックを取得するとき、内部状態を (スレッドセーフな方法で) 変更して、「多数のリーダーとnand単一ライター」の期待を維持します (おそらく、それが可能になるまでブロックします。つまり、競合するロックが撤回されます)。

于 2011-04-20T06:52:47.640 に答える