UDP経由でメッセージを受信しています。メッセージはと非常に、つまり1msごとにすぐに届く可能性があります(ただし、これはさまざまです)。メッセージが受信されると、イベントが呼び出されます。TaskFactory()。StartNew()作成順に終了
private static void OnMessageReceived(object sender, UDPMessage message)
{
MessageQueue.Enqueue(message);
}
このように、受信したメッセージは処理されるキューに入れられます。私はこれを行う - そして、これが間違っているかどうかわからない - UDP受信スレッドが自由に次のメッセージを受信できるようにする(私は受信スレッドをブロックし、メッセージ)。メッセージがキューに登録されたときに、MessageQueued
イベントが発生した
:
private static void MessageQueued(object sender, EventArgs e)
{
var processTask = new TaskFactory().StartNew(ProcessMessage);
}
ProcessMessage
は処理のビットを行い、その後、順序でこれらのメッセージは、別のアプリケーション ...にメッセージを送信他のアプリケーションに到着することが重要です。
メッセージが非常に早く到着した場合、作成されたタスクの完了順序は、作成された順序と同じではないことが懸念されます。
メッセージが到着する順序でタスクが作成され、 が確実に同じ順序でメッセージを転送するようにする必要があります。
(はい、私はUDPメッセージを保証し、彼らが送られたのと同じ順序で到着するが、それを忘れていないことを認識しています;))
フォームそれは、私は待つ必要があると思うように聞こえる何を前のタスクが完了するまで、現在のタスクを完了としてマークする前に...私は、現在のタスクを開始する前に前のタスクが完了するのを待っていません。
これは意味があると思います!
var ProcessMessageQueueLoop = new TaskFactory().StartNew(ProcessMessageQueueThread);
private static void ProcessMessageQueueThread()
{
while (true)
{
if (MessageQueue.Count > 0)
{
ProcessMessage();
}
}
}
private static void OnMessageReceived(object sender, UDPMessage message)
{
MessageQueue.Enqueue(message);
}
:コメントに基づいて
更新
まあ、私は当初、常にメッセージキューをチェックした項目が利用可能であった場合は、デキューし、それを加工したタスクによって作成されたループを、持っていませんでした
これが正しいかどうかはわかりませんでしたので、少し遊んだので、私の質問です。
「Task.Run(...)」などの静的ヘルパーを使用してみませんか? – Aybe
パケットが到着する順序でタスクが完了していることを確認することは、udpパケットを受信していない場合に発生します。私はあなたが "それを無視する"と言っているのを知っていますが、それを注文しようとするのは何ですか?だから、ループ内のメッセージを処理し、新しいメッセージをキューから取り出すバックグラウンドスレッドが1つだけ必要であると思われます。 – Blam
また、ProcessMessageが他のすべてのメッセージと全く同じ時間に各メッセージを処理しない限り、処理中のメッセージの順序とは異なる順序でメッセージをキューに入れることができます。特定の順序でメッセージを生成する必要がある場合は、メッセージを非同期に処理する必要はありません。 –