スピンウェイトとスリープ待機。どちらを使うべき?
質問
効率的なのは
SpinWait.SpinUntil(() => myPredicate(), 10000)
タイムアウト10000msの場合
または
を使う方が効率的でしょうか?
Thread.Sleep
を使う方が効率的でしょうか?
例えば、以下のようなものです。
SleepWait
関数を使用します。
public bool SleepWait(int timeOut)
{
Stopwatch stopwatch = new Stopwatch();
stopwatch.Start();
while (!myPredicate() && stopwatch.ElapsedMilliseconds < timeOut)
{
Thread.Sleep(50)
}
return myPredicate()
}
私は、1sec以上のタイムアウトについて話している場合、SpinWaitのすべての降伏は良い使用パターンではないかもしれないことを懸念しています?これは有効な仮定でしょうか?
どのアプローチが好きですか、そしてそれはなぜですか?また、さらに良いアプローチはありますか?
更新 - より具体的になる。
BlockingCollection が制限された容量に達したときにスリーピングスレッドをパルスさせる方法はありますか?私はむしろ、Marc Gravel が提案するように、ビジーウェイトを完全に回避します。
どのように解決するのですか?
この
ベスト
を実現するための何らかのメカニズムを持つことです。
を積極的に検出する
を検出するメカニズムが必要です。
になる
が真になるのを受動的にポーリングするのではなく); これは任意の種類の待ちハンドルかもしれませんし、あるいは
Task
で
Wait
とか、あるいは
event
を購読して、自分自身を解き放つことができるのです。もちろん、そのような "何かが起こるまで待つ" を行う場合、それはつまり
やはり
単に次の作業をさせるのと同じように効率的ではない
をコールバックとして
つまり、待つためにスレッドを使用する必要はないのです。
Task
には
ContinueWith
を使うか、あるいは、その作業を
event
で行うこともできます。その
event
は、文脈にもよりますが、おそらく最もシンプルなアプローチでしょう。
Task
は、タイムアウトを伴う待機とコールバックの両方のメカニズムを含む、ここで話しているほとんどすべてのものを既に提供しています。
そして、はい、10秒間スピンすることは素晴らしいことではありません。現在のコードのようなものを使用したい場合、そして短い遅延を期待する理由があり、より長い遅延を許容する必要がある場合、おそらく
SpinWait
を (たとえば) 20ms の間、そして
Sleep
を使用するのですか?
コメントについて; 私がどのように "is it full" メカニズムをフックするかは以下の通りです。
private readonly object syncLock = new object();
public bool WaitUntilFull(int timeout) {
if(CollectionIsFull) return true; // I'm assuming we can call this safely
lock(syncLock) {
if(CollectionIsFull) return true;
return Monitor.Wait(syncLock, timeout);
}
}
で、"put back into the collection"のコードで。
if(CollectionIsFull) {
lock(syncLock) {
if(CollectionIsFull) { // double-check with the lock
Monitor.PulseAll(syncLock);
}
}
}
関連
-
[解決済み】Ajax処理で「無効なJSONプリミティブ」と表示される件
-
[解決済み】C#で四捨五入する方法
-
[解決済み】MetadataException: 指定されたメタデータ・リソースをロードできない
-
[解決済み] [Solved] .NETでスレッドの終了を待つには?
-
[解決済み] IDisposable インターフェースの正しい使用法
-
[解決済み] wait()とsleep()の違いについて
-
[解決済み] async」と「await」の使い方とタイミング
-
[解決済み] あるコンストラクタを別のコンストラクタから呼び出す
-
[解決済み] ThreadLocal変数はいつ、どのように使用すればよいですか?
-
[解決済み] イールドリターン」の正しい使い方
最新
-
nginxです。[emerg] 0.0.0.0:80 への bind() に失敗しました (98: アドレスは既に使用中です)
-
htmlページでギリシャ文字を使うには
-
ピュアhtml+cssでの要素読み込み効果
-
純粋なhtml + cssで五輪を実現するサンプルコード
-
ナビゲーションバー・ドロップダウンメニューのHTML+CSSサンプルコード
-
タイピング効果を実現するピュアhtml+css
-
htmlの選択ボックスのプレースホルダー作成に関する質問
-
html css3 伸縮しない 画像表示効果
-
トップナビゲーションバーメニュー作成用HTML+CSS
-
html+css 実装 サイバーパンク風ボタン
おすすめ
-
[解決済み】プログラム実行中に1秒待つ
-
[解決済み】スクリプトクラスが見つからないので、スクリプトコンポーネントを追加できない?
-
[解決済み】C#で四捨五入する方法
-
[解決済み] 保護レベルによりアクセス不能になりました。
-
[解決済み】SmtpException: トランスポート接続からデータを読み取れません:net_io_connectionclosed
-
[解決済み】「入力文字列が正しい形式ではありませんでした」エラーの解決方法は?[重複しています]。
-
[解決済み】Sequence contains no matching element(シーケンスにマッチする要素がない
-
[解決済み】 C# 条件演算子エラー 代入、call、increment、decrement、await、new object 式のみ文として使用可能です。
-
[解決済み】パラメータ付きRedirectToAction
-
[解決済み】IntPtrとは一体何なのか?