7

完全なコードはこちら: http://pastebin.com/MM3vWmqA

関数 fast_generator では、2 つのステートメントにコメントを追加しました。これらのステートメントを切り替えると、コードは最大 1.8 倍速く実行されます。最初のステートメントを削除すると、コードは元のバージョンよりも高速に実行されますが、切り替えた場合に比べて遅くなります。

テストケースは次のとおりです。

最初 - 最も遅い。452ms。

counter++;
i--;

2 番目 - 最初のものよりも高速です。280ms。

i--;
counter++;

3 番目 - 1 番目よりも高速ですが、2 番目よりも低速です。421ms。

i--;

元のステートメントのアセンブラー出力は次のとおりです。

inc edx
mov eax, 6

これらのステートメントを切り替えても、アセンブラーの出力は同じままであり、これらの asm 命令の唯一の違いが交換されることを確認しました。

VC++10 と VC++11 でテストしましたが、同じ動作です。これらのステートメントを切り替えるとアルゴリズムが約 1.8 倍高速化される理由を誰か説明できますか? std::clock() が正確ではないと思われる場合は、size = 7 に変更してください。私のマシンでは、size = 7 の違いは 12000ms と 7000ms です。

4

1 に答える 1

3

あなたの遅い例はi、ループの開始時に配列にインデックスを付けるために使用する直前にデクリメントしています。あなたの速い例は、介在するステップを追加します。プロセッサの内部アーキテクチャに関与していないため、確実に知ることはできませんが、最も可能性が高いのは、プロセッサが既にbuffer[i]パイプラインに持っていることですが、デクリメントによってその値が無効になり、パイプライン ストールが発生します。介在するステップにより、必要になる前に正しい値を回復する時間が増えます。

ところで、mov eax, 5を行っている命令ではありませんかi--。コンパイラを持たない私たちのために、アセンブリのコンテキストをもっと投稿すると役に立ちます。

于 2012-04-04T22:13:44.063 に答える