2つのスレッドによって生成されたタイムスタンプ

私は自分のコードに2つのスレッドがあります。 1つのスレッドはメッセージを生成するジェネレータです。タイムスタンプは、メッセージが送信される前に生成されます。もう1つのスレッドは、複数のクライアントからの応答を受け取る受信機です。各返信に対してタイムスタンプが作成されます。 2つのスレッドが同時に実行されています。

受信者によって生成されたタイムスタンプは、ジェネレータによって生成されたタイムスタンプより早いことがわかりました。正しい順序は、レシーバのタイムスタンプがジェネレータのタイムスタンプより遅いものでなければなりません。

私がジェネレータースレッドの優先度を高くした場合、この問題は発生しません。しかし、これによりパフォーマンスが低下する可能性もあります。

正しい順序とパフォーマンスの低下を保証する他の方法はありますか?ありがとう。

0
プロデューサのタイムスタンプがメッセージに格納されている場合、プロデューサとコンシューマのタイムスタンプは同じ方法で生成され、両方の時間はコンシューマで読み込み/表示されますが、これが起こるのを見ることができる唯一の方法は時間が逆転する場合です。あなたはニュートリノ実験をしていますか?
追加された 著者 Martin James,
この種の問題は、通常、プログラミング言語とOSにかなり依存しています。どのようなプログラミング言語で、どのOSの下で作業していますか?
追加された 著者 D.Shawley,
@MartinJames - これは、メッセージがエンキューされ、クロックの解像度より小さい時間内にデキューされた場合、またはJVMオプティマイザがタイムスタンプを生成し、宣言のポイントより早くキャッ​​シュする場合に発生します。
追加された 著者 D.Shawley,
私はJavaを使用し、Windows XP上で実行しています
追加された 著者 susan,
その後、それを修正する方法は?
追加された 著者 susan,

1 答え

問題のコメントスレッドに基づいて、これはおそらくオプティマイザの効果です。これは実際には何よりもデザインの問題です。プロデューサとコンシューマ間のクロックが共有されているか、緊密に同期されていることを前提としています。この仮定は、複数のコンピュータ間で処理を分散する必要があるまでは妥当と思われます。

クロックは、異なるコンピュータ間で緊密に同期することはめったにありません。コンピュータを同期させるための一般的なアルゴリズムは、ネットワークタイムプロトコルです。ローカルエリアネットワークでは非常に近いミリ秒の同期を達成できますが、それでも困難です。

この問題には2つの解決策があります。 1つは、プロデューサのタイムスタンプをクライアントと受信者に渡すことです。受信者が現在時刻という概念より早いタイムスタンプを受信した場合、タイムスタンプは現在の時刻にリセットされます。このタイプの正規化は、単調に増加するシーケンスが保持され続ける時間についての仮定を可能にする。

もう1つの解決策は最適化を無効にし、問題がなくなることを期待することです。ご想像のとおり、このソリューションを使用すると、あなたの走行距離は大きく変わることがあります。

解決しようとしている問題によっては、異なるスレッド間で独自の時計を同期させることができます。 壁の時間ではなく、原子的に増分する数字を使用します。 java.util.concurrent.atomic.AtomicInteger またはその親子の1つを使用して、メッセージが生成されるたびにインクリメントされる単一の数値を提供することができます。これにより、プロデューサとレシーバは、ソートのクロックとして使用する共有値を持つことができます。

いずれにしても、特に同期のためにクロックを正しく使用することは本当に困難です。分散システムからの時間に関する前提を取り除く何らかの方法を見つけることができれば、アーキテクチャーとソリューションはより弾力性とより決定性になります。

0
追加された