3

私の研究から、飢餓、デッドロック、公平性、およびその他の並行性の問題の概念を知っています。ただし、理論は実践とはある程度異なります。また、実際のエンジニアリング タスクには、学術的なものよりも詳細な作業が含まれることがよくあります...

C++ 開発者として、私はスレッド化の問題についてしばらく心配していました...

xプログラムのメモリの大部分を参照する共有変数があるとします。変数は 2 つのスレッドAとの間で共有されBます。

ここで、スレッドとスレッドのx両方からの読み取り/書き込み操作を考えると、おそらく同時に、これらの操作を同期する必要がありますよね? したがって、へのアクセスには、たとえばミューテックスを使用して達成できる何らかの形式の同期が必要です。ABx

ここで、xが最初に thread によって書き込まれ、次に(何らかの方法で)Aスレッドに渡され、そのスレッドが のみを読み取るという別のシナリオを考えてみましょう。次にスレッドは、 calledへの応答を生成し、それをスレッドに返します(これも何らかの形で)。私の質問は、このシナリオをスレッドセーフにするためにどの同期プリミティブを使用する必要があるかということです。アトミックと、さらに重要なメモリ フェンスについて読んだことがありますが、これらは信頼できるツールですか?BxBxyA

これは、「クリティカル セクション」が存在する典型的なシナリオではありません。代わりに、一部のデータがスレッド間で渡され、同じメモリ位置に同時に書き込みが行われる可能性はありません。したがって、書き込まれた後、データは最初に何らかの形で「フラッシュ」され、他のスレッドが読み取り前に有効で一貫した状態でデータを確認できるようにする必要があります。文学ではどのように呼ばれていますか、それは「可視性」ですか?

pthread_onceそのBoost/stdの対応物、つまりcall_once. 「1回」機能によってアクセスされる一種の「メッセージキュー」を介してスレッド間でxとの両方が渡される場合、それは役立ちますか。y私の知る限り、それは一種のメモリフェンスとして機能しますが、これについての確認は見つかりませんでした.

CPU キャッシュとその一貫性はどうですか? エンジニアリングの観点から、それについて何を知っておくべきですか? そのような知識は、上記のシナリオ、または C++ 開発で一般的に遭遇するその他のシナリオで役立ちますか?

多くのトピックを混在させている可能性があることは承知していますが、既知のパターンを再利用できるように、一般的なエンジニアリング プラクティスとは何かをよりよく理解したいと考えています。

この質問は、主に C++03 の状況に関連しています。これは私の日常の職場環境です。私のプロジェクトは主に Linux を使用するため、Boost.Atomic を含む pthread と Boost のみを使用できます。しかし、C++11 の登場により、そのような点に関して何か変化があったかどうかにも興味があります。

質問が抽象的であり、それほど正確ではないことは知っていますが、どんな入力も役立つ可能性があります。

4

1 に答える 1

10

あなたは共有変数 x を持っています

それがあなたが間違っているところです。ある種のスレッドセーフなコンシューマー/プロデューサー キューを使用して作業項目の所有権を渡すと、スレッド化がはるかに簡単になります。すべてのビジネス ロジックを含むプログラムの残りの部分からは、何も共有されません。

メッセージの受け渡しは、キャッシュの衝突を防ぐのにも役立ちます (プロデューサー/コンシューマー キュー自体を除いて真の共有はなく、作業単位が大きい場合はパフォーマンスにわずかな影響があるため)、データをメッセージに編成することで false を減らすことができます。共有)。

並列処理は、問題をサブ問題に分割するときに最適にスケーリングされます。小さなサブ問題も、推論がはるかに簡単です。

あなたはすでにこれらの方針に沿って考えているようですが、そうではありません。アトミック、ミューテックス、フェンスなどのスレッド化プリミティブは、メッセージ パッシングを使用するアプリケーションにはあまり適していません。実際のキューの実装を見つけます (キュー、循環リング、ディスラプター、それらは異なる名前で呼ばれますが、すべて同じニーズを満たします)。プリミティブはキューの実装内で使用されますが、アプリケーション コードでは使用されません。

于 2014-10-31T23:16:58.883 に答える