複数読み出し時の排他書き込みシンクロナイザを使用する
スレッドの調整:インデックス への移動
クリティカルセクションを使ってグローバルメモリを保護しているときには,一度に 1 つのスレッドしかメモリを使用できません。これはユーザーが必要とする保護よりも過剰な保護となる場合があります。特に,頻繁に読み取るけれどほとんど書き込まないオブジェクトや変数に対して効果がある場合があります。複数のスレッドが同じメモリを同時に読み取っても,書き込みを行うスレッドがない限りは危険はありません。
頻繁に読み取るけれどほとんど書き込まないグローバルメモリがある場合,System.SysUtils.TMultiReadExclusiveWriteSynchronizer を使って保護できます。このオブジェクトはクリティカルセクションのように動作しますが,書き込みを行うスレッドがない限り,複数のスレッドが保護されているメモリを読み取ることを許可します。スレッドは,TMultiReadExclusiveWriteSynchronizer によって保護されているメモリに書き込むためには,排他的アクセスを持っていなければなりません。
複数読み取り時の排他書き込みシンクロナイザを使用するには,保護したいグローバルメモリと関連付けられている TMultiReadExclusiveWriteSynchronizer のグローバルインスタンスを作成します。このメモリから読み取りを行うすべてのスレッドは,最初に BeginRead メソッドを呼び出さなければなりません。BeginRead は,現在ほかのスレッドがメモリに書き込みを行っていないことを確認します。スレッドが保護されているメモリからの読み取りを終了すると,EndRead メソッドを呼び出します。保護されているメモリに書き込みを行うすべてのスレッドは,最初に BeginWrite を呼び出す必要があります。BeginWrite は,現在ほかのスレッドがメモリの読み取りまたは書き込みを行っていないことを確認します。スレッドは,保護されているメモリへの書き込みを終了すると,EndWrite メソッドを呼び出します。これにより,メモリの読み取りを待っているスレッドが処理を実行できるようになります。
警告: クリティカルセクションと同様に,複数読み取り時の排他書き込みシンクロナイザが機能するのは,すべてのスレッドが,このシンクロナイザを使って関連付けられたグローバルメモリにアクセスする場合だけです。シンクロナイザを無視して,BeginRead または BeginWrite を呼び出さずにグローバルメモリにアクセスするスレッドがある場合は,同時アクセスの問題が発生します。