[解決済み] if...else if文を確率で並べるとどのような効果がありますか?
質問
具体的には、もし私が一連の
if
...
else if
と評価される相対的な確率があらかじめわかっています。
true
確率の高い順に並べると、実行時間にどれくらいの差が出るのでしょうか?例えば、このようにした方がいいでしょうか。
if (highly_likely)
//do something
else if (somewhat_likely)
//do something
else if (unlikely)
//do something
をこれか?
if (unlikely)
//do something
else if (somewhat_likely)
//do something
else if (highly_likely)
//do something
ソートされた方が速いのは明らかですが、読みやすさや副作用の存在を考えると、最適でない並び方をしたい場合もあります。また、CPUが分岐予測をどの程度行うかは、実際にコードを動かしてみないとわからない。
ということで、具体的なケースを想定して、自分なりの答えを出しましたが、他の方のご意見・ご感想も伺えればと思います。
重要:この質問は
if
文は、プログラムの動作に他の影響を与えることなく、任意に並べ替えが可能です。私の答えでは、3つの条件テストは相互に排他的であり、副作用は生じません。確かに、ある目的の動作を達成するために、ある順序で文を評価しなければならないのであれば、効率の問題は無意味です。
どのように解決するのですか?
一般的なルールとして、すべてのIntel CPUは、最初に見たとき、順方向分岐は取られないと仮定します。 以下を参照してください。 ゴッドボルトの研究 .
その後、枝は枝予測キャッシュに入り、過去の動作が将来の枝予測に利用されます。
つまり、タイトなループの中では、ミスオーダーの影響は比較的小さいと言えます。 分岐予測器は、どの分岐が最も可能性が高いかを学習し、ループ内で自明でない量の作業がある場合、小さな差はそれほど大きくはなりません。
一般的なコードでは、ほとんどのコンパイラはデフォルトで(他に理由がない限り)、生成される機械語コードの順番を、あなたのコードで並べたのとほぼ同じにします。 したがって、if文は失敗すると前方に分岐します。
ですから、"first encounter"から最適な分岐予測を得るためには、可能性の低い順に並べる必要があります。
ある条件下で何度もループするようなマイクロベンチマークでは、命令数などの影響が小さく、相対的な分岐予測の問題はほとんど発生しません。 そこで、このような場合 プロファイル 経験則は当てにならないので。
その上、ベクトル化やその他多くの最適化が、小さなタイトループに適用されます。
そのため、一般的なコードでは、最も可能性の高いコードを
if
ブロックに入れることで、キャッシュされない分岐予測のミスが最も少なくなります。 タイトなループでは、まず一般的なルールに従い、それ以上の知識が必要な場合は、プロファイルを作成する以外に方法はありません。
もちろん、あるテストが他のテストよりはるかに安い場合は、すべてが水の泡になります。
関連
-
[解決済み】C++コンパイルタイムエラー:数値定数の前に期待される識別子
-
[解決済み】C++ - ステートメントがオーバーロードされた関数のアドレスを解決できない。
-
[解決済み】システムが指定されたファイルを見つけられませんでした。
-
[解決済み] explicit キーワードの意味は?
-
[解決済み] callとapplyの違いは何ですか?
-
[解決済み] ルール・オブ・スリーとは?
-
[解決済み] コピーアンドスワップ慣用句とは?
-
[解決済み] C++でextern "C "を使用した場合の効果は?
-
[解決済み] HTMLの "role "属性は何のためにあるのですか?
-
[解決済み】C/C++の"-->"演算子とは何ですか?
最新
-
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 実装 サイバーパンク風ボタン
おすすめ
-
[解決済み】 unsigned int vs. size_t
-
[解決済み】識別子 "string "は未定義?
-
[解決済み】致命的なエラー LNK1169: ゲームプログラミングで1つ以上の多重定義されたシンボルが発見された
-
[解決済み】C++の変数はイニシャライザーを持っているが、不完全な型?
-
[解決済み】Visual C++で "Debug Assertion failed "の原因となる行を見つける。
-
[解決済み】リンカーエラーです。"リンカ入力ファイルはリンクが行われていないため未使用"、そのファイル内の関数への未定義参照
-
[解決済み】指定範囲内の乱数で配列を埋める(C++)
-
[解決済み】Visual Studioのデバッガーエラー。プログラムを開始できません 指定されたファイルが見つかりません
-
[解決済み】Eclipse IDEでC++エラー「nullptrはこのスコープで宣言されていません」が発生する件
-
[解決済み] Linuxカーネルのprocess/unlikelyマクロはどのように動作し、どのような利点があるのでしょうか?