0

リアルタイムのイベント メッセージを高速で処理するメソッドがあるとします。

各呼び出し (メッセージが届く) ごとに、追跡したい複数の状態があり、メソッドの次の呼び出しで実行する処理の種類は現在の状態によって異なります。

レートが高く、単一スレッドでの処理に時間がかかる可能性があるため、前の呼び出しが次の呼び出しの前に終了しない場合があります。

各メソッド呼び出しに非同期マルチスレッド実装 (スレッド プールなど) を使用すると、複数の呼び出しが同時に実行される可能性があり、それらのそれぞれが同じ状態に評価され、同じ種類の処理が発生します。私が欲しいものではありません。スレッド呼び出しの 1 つで変数の状態が変更された場合、他のスレッドがその状態を認識できるようにしたいと考えています。

私の質問は、レートと呼び出しごとの処理を非同期で処理することを確認したいが、同時に「同時に」スレッドへの複数の呼び出しが状態を認識していることを確認してください。順序はそれほど重要ではありません。

すなわち:

state = false;//current state

a thread                     b thread (and vice versa if thread b or thread a "saw" it first)
------------------------------
|                            |
|                            |
sees false                  sees false (should "see" true)
changes to true             changes to true (should not change to true)
|                            |


void processMessage(String message) {
    Runnable runner = new Runnable() {
       void run() {
        if(track.in_state == true) {
          if(track.state == 1) {
             track.in_state = false;
             //do something here
          }
          else if(track.state == 2) {
             track.in_state = false;
             //do something here
          }
        }
      }
    }
    poolA.executor(runner);
    //what happens here is that multiple threads are executed with same processing here
}

void processADifferentMessage(String message) {//a different but also dependent on the state tracker object
    Runnable runner = new Runnable() {
       void run() {
        if(track.in_state == false) {
             //do something here
        }
       }
    };
    //I also want to make sure that its state aware here as well in this thread pool
    poolB.executor(runner);
}

返信ありがとうございます。

4

2 に答える 2

0

演算子を使用して、AtomicBooleanおよびを使用できます。AtomicIntegercompareAndSet

AtomicBoolean atomicBoolean;
AtomicInteger atomicInteger;
void processMessage(String message) {
    Runnable runner = new ... {
        boolean success = false;
        boolean boolState;
        int intState;
        while(!success) {
            boolState = atomicBoolean.get();
            success = atomicBoolean.compareAndSet(boolState, !boolState);
        }
        success = false
        while(!success) {
            intState = atomicInteger.get();
            success = atomicInteger.compareAndSet(intState, (intState + 1) % maxIntState);
        }
        if(boolState) {
          if(intState == 1) {
             //do something here
          }
          else if(intState == 2) {
             //do something here
          }
        }
    }
    poolA.executor(runner);
}

whileループはAtomicBooleanandの状態を読み取り、AtomicIntegerそれらを新しい状態に更新します。AtomicBoolean毎回の状態を true と false の間で切り替え、AtomicIntegerを 0 に初期化し、次に到達するまでインクリメントすると想定していますmaxIntState。ポイントを0にリセットします(たとえば、maxIntStateが4の場合AtomicInteger、0 -> 1 -> 2 -> 3 -> 0になります)。while状態を読み取ってから状態を更新しようとするまでの間に別のスレッドが状態を変更した場合に備えて、ここでループを使用します (たとえばintState、1 の値を読み取っても、別のスレッドintStateが 2 に更新する前に更新します)。それを更新してから、intStateの 2) で再試行します)

于 2013-07-06T17:57:11.313 に答える
0

あなたが述べた現在の問題は、AtomicInteger と AtomicBoolean を使用して解決できる可能性があります。

しかし、いくつかの状態に応じていくつかのメッセージを処理/処理する必要があり、いくつかの状態に基づいて同時に実行される可能性がある、ある種の非同期モデルが必要だと思います。これらのタイプのシナリオでは、atomicInteger と AtomicBoolean では実行できない状態によっては、wait/notify/await/signal を使用する必要がある場合があるため、atomic バージョンを使用するよりも lock/synchronized の方が適しています。その要件がさらに進んでいる可能性があります。

于 2013-07-06T18:05:46.353 に答える