48

マルチ CPU システムで微分方程式を解く Fortran プログラムのパフォーマンスを測定するよう依頼されました。私の雇用主は、私が FLOP/s (Floating operations per second) を測定し、その結果をベンチマーク ( LINPACK ) と比較することを主張していますが、誰も私に FLOP が何であるかを説明できないという理由だけで、それが正しい方法であるとは確信していません。

私は FLOP とは何かについて調査を行いましたが、かなり矛盾した答えが得られました。私が得た最も人気のある答えの 1 つは、「1 FLOP = 加算と乗算演算」でした。本当?もしそうなら、物理的に、それは正確には何を意味するのでしょうか?

最終的に使用する方法が何であれ、それはスケーラブルでなければなりません。コードの一部のバージョンは、数百万の未知数を持つシステムを解決し、実行に数日かかります。

私の場合、パフォーマンスを測定する他の効果的な方法は何でしょうか(私の場合の要約は、「数百のCPUで何日も何度も何度も多くの算術計算を行うfortranコードです)?

4

9 に答える 9

56

それが何を測定するのかを正確に理解している限り、それはパフォーマンスのかなりまともな測定値です.

FLOPS は、その名前が 1 秒あたりの浮動小数点演算回数を意味するように、FLOP を構成するものは CPU によって異なる場合があります。(一部の CPU は加算と乗算を 1 つの操作として実行できますが、他の CPU は実行できません)。つまり、パフォーマンスの尺度として、ハードウェアにかなり近いことを意味します。つまり、1) 与えられたアーキテクチャで理想的な FLOPS を計算するにはハードウェアを知っている必要があり、その方法を理解するにはアルゴリズムと実装を知っている必要があります。実際に構成されている多くの浮動小数点演算。

いずれにせよ、CPU の使用状況を調べるのに便利なツールです。FLOPS での CPU の理論上のピーク パフォーマンスを知っていれば、効率的に利用するのが難しいことが多い CPU の浮動小数点ユニットをどれだけ効率的に使用しているかがわかります。CPU が処理できる FLOPS の 30% を実行するプログラムには、最適化の余地があります。70% で実行されるものは、基本的なアルゴリズムを変更しない限り、おそらくそれほど効率的ではありません。あなたのような数学の多いアルゴリズムの場合、これはパフォーマンスを測定する標準的な方法です。プログラムの実行にかかる時間を単純に測定することもできますが、それは CPU によって大きく異なります。しかし、プログラムの CPU 使用率が (ピーク FLOPS カウントと比較して) 50% である場合、それはやや一定の値になります (

しかし、「私の CPU は X GFLOPS の能力があり、実際にはその 20% のスループットしか達成していない」ということを知っていることは、高性能ソフトウェアでは非常に貴重な情報です。これは、浮動小数点演算以外の何かがあなたを妨げており、FP ユニットが効率的に機能していないことを意味します。そして、FP ユニットが作業の大部分を構成しているため、それはソフトウェアに問題があることを意味します。

「私のプログラムは X 分で実行される」を測定するのは簡単です。それが受け入れられないと感じた場合は、「それを 30% 削減できるだろうか」と考えても構いませんが、そうでない限り、それが可能かどうかはわかりません。どのくらいの作業が行われているか、CPU がピーク時にどれだけの能力を発揮できるかを正確に把握できます。CPU が基本的に毎秒これ以上の命令を実行できるかどうかさえわからない場合、これを最適化するのにどれくらいの時間を費やしたいでしょうか?

CPU の FP ユニットが効率的に使用されないようにするのは非常に簡単です。FP op 間の依存関係が多すぎるか、ブランチが多すぎるか、効率的なスケジューリングが妨げられます。それが実装を妨げているのであれば、それを知る必要があります。「可能なはずの FP スループットが得られていないため、CPU が FP 命令を発行する準備ができているときに、コードの他の部分が明らかに FP 命令を使用できないようにしている」ことを知っておく必要があります。

他の方法でパフォーマンスを測定する必要があるのはなぜですか? 上司に言われたとおりに FLOPS カウントを計算することの何が問題になっていますか? ;)

于 2008-11-30T18:53:45.227 に答える
30

細かい点をいくつか追加したいと思います。

  • 部門は特別です。ほとんどのプロセッサは 1 つのサイクルで加算、比較、または乗算を実行できるため、これらはすべて 1 つのフロップとしてカウントされます。しかし、分割には常に時間がかかります。どのくらい長くなるかはプロセッサによって異なりますが、HPC コミュニティには、1 ディビジョンを 4 フロップとしてカウントするというデファクト スタンダードのようなものがあります。

  • プロセッサーに乗算と加算を 1 つの命令で実行する融合乗算加算命令がある場合 (通常は A += B * C)、これは 2 つの演算としてカウントされます。

  • 単精度フロップと倍精度フロップの区別には常に注意してください。非常に多くの単精度ギガフロップスを処理できるプロセッサは、その多くの倍精度ギガフロップスのごく一部しか処理できない場合があります。AMD Athlon および Phenom プロセッサは、通常、単精度の半分の倍精度フロップを実行できます。ATI Firestream プロセッサは、通常、単精度の 1/5 倍精度のフロップを実行できます。誰かがあなたにプロセッサーやソフトウェアパッケージを売り込もうとしていて、彼らがどちらかを言わずにフロップを引用するだけなら、あなたは彼らに電話するべきです.

  • メガフロップ、ギガフロップ、テラフロップなどの用語が一般的に使用されています。これらは1024ではなく1000の因数を指します。たとえば、1 メガフロップ = 1,000,000 フロップ/秒であり、1,048,576 ではありません。ディスク ドライブのサイズと同様に、これについても混乱が生じます。

于 2008-11-30T19:53:48.927 に答える
9

古い質問で、人気がある場合は、正確に素晴らしいとは言えない古い回答、IMO。

「FLOP」は浮動小数点演算です。「FLOPS」は、次の 2 つのいずれかを意味します。

  • 「FLOP」の単純な複数形 (つまり、「操作Xには 50 FLOP が必要です」)
  • 最初の意味での FLOPのレート(つまり、1 秒あたりの浮動小数点演算操作)

文脈から明確でない場合は、前者を「FLOPs」、後者を「FLOP/s」と書くことで、どちらを意味するかを明確にすることがよくあります。

FLOP は、整数演算、論理演算、ビット演算、メモリ演算、分岐演算などの他の種類の CPU 演算と区別するために呼ばれています。彼ら。

「FLOP カウント」の慣習は、科学計算のごく初期の時代にまでさかのぼります。当時、FLOP は比較的高価で、それぞれに多くの CPU サイクルが必要でした。たとえば、80387 演算コプロセッサは、1 回の乗算に約 300 サイクルかかりました。これは、パイプライン処理が行われる前、CPU クロック速度とメモリ速度の間のギャップが実際に開く前の時点でした。メモリ操作は 1 ~ 2 サイクルしかかからず、分岐 (「意思決定」) も同様に低コストでした。当時、十数回のメモリアクセスを優先して単一の FLOP を排除できれば、利益が得られました。ダースの分岐を優先して 1 つの FLOP を排除できれば、利益が得られます。そう、以前は、FLOP をカウントし、メモリ参照と分岐についてあまり心配しないことが理にかなっていました。なぜなら、FLOP は他の種類の操作に比べて個別に非常にコストがかかるため、実行時間を大きく支配していたからです。

最近では、状況が逆転しています。FLOP は非常に安価になりました — 最新の Intelコアは 1 サイクルあたり約 2 FLOP を実行できます (ただし、除算は比較的高価なままです) — メモリ アクセスと分岐は比較的高価です: L1 キャッシュ ヒットのコストはおそらく 3 または 4 サイクル、メインメモリのコストは 150 ~ 200 です。この逆を考えると、メモリ アクセスを優先して FLOP を削除しても利益が得られるわけではありません。実際、それはありそうもありません。同様に、FLOP を実行するかどうかを決定するよりも、FLOP が冗長であっても「実行するだけ」の方がコストがかからないことがよくあります。これは、25 年前とはまったく逆の状況です。

残念ながら、アルゴリズムのメリットの絶対的な測定基準としてのブラインド FLOP カウントの慣行は、販売期限を過ぎても存続しています。現代の科学計算は、FLOP の数を減らすことよりも、メモリ帯域幅の管理(FLOP を実行する実行ユニットに常にデータを供給し続けようとすること)に重点を置いています。LINPACKへの参照(基本的にLAPACKによって廃止されました)20 年前) あなたの雇用主はおそらく非常に古い学校の出身であり、パフォーマンスの期待値を確立することはもはや FLOP カウントの問題ではないという事実を内面化していないのではないかと私は思います. 2 倍の FLOP を実行するソルバーは、メモリ アクセス パターンとデータ レイアウトがはるかに有利であれば、別のソルバーよりも 20 倍高速である可能性があります。

これらすべての結果として、計算集約型ソフトウェアのパフォーマンス評価は、以前よりもはるかに複雑になっています。FLOP が安価になったという事実は、メモリ操作と分岐のコストが大幅に変動するため、非常に複雑です。アルゴリズムの評価に関して言えば、単純な FLOP カウントでは、全体的なパフォーマンスの期待値がわかりません。

おそらく、パフォーマンスの期待値と評価について考えるより良い方法は、いわゆるルーフライン モデルによって提供されます。これは完璧にはほど遠いですが、浮動小数点とメモリ帯域幅の問題の間のトレードオフについて考えさせるという利点があります。同時に、パフォーマンス測定値とパフォーマンス期待値の比較を可能にする、より有益で洞察に満ちた「2D 画像」を提供します。

一見の価値があります。

于 2013-09-01T23:33:32.410 に答える
4

「結果をベンチマークと比較」して、何をしますか?

FLOPSはあなたが必要とすることを意味します

1) ある作業単位あたりの FLOP。

2) その作業単位の時間。

ループを 1,000 回繰り返す入力ファイルがあるとします。ループは便利な作業単位です。1,000回実行されます。1時間かかります。

ループには、いくつかの加算と乗算、およびいくつかの除算と平方根があります。足し算、掛け算、割り算ができます。+、*、および / を探して、ソースでこれを数えることができます。コンパイラからのアセンブラ言語の出力を見つけて、そこでカウントすることもできます。異なる番号を取得する場合があります。どちらが正しいですか?上司に聞いてください。

平方根を数えることはできますが、乗算と加算に関して実際に何をするかはわかりません。したがって、平方根にかかる時間を把握するには、ベンチマーク乗算と平方根の比較などを行う必要があります。

これで、ループ内の FLOPS がわかります。そして、それを 1,000 回実行する時間を知っています。1 秒あたりの FLOPS がわかります。

次に、LINPACK を見て、速度が遅いことがわかります。それで?あなたのプログラムは LINPACK ではなく、LINPACK より遅いです。コードが遅くなる可能性は非常に高いです。コードが LINPACK と同じ年数にわたって記述および最適化されていない限り、遅くなります。

これが他の部分です。お使いのプロセッサには、さまざまなベンチマークに対して定義された FLOPS 評価があります。あなたのアルゴリズムはそれらのベンチマークの 1 つではないため、ベンチマークに達していません。これは悪いですか?それとも、これはベンチマークではないことの明らかな結果ですか?

実行可能な結果はどうなりますか?

ベンチマークコードベースに対する測定は、アルゴリズムがベンチマークアルゴリズムではないことを示すだけです。あなたが違うというのは当然の結論です。通常は遅くなります。

明らかに、LINPACK に対して測定した結果は、(a) 異なるため、(b) 最適化する必要があります。

測定は、自分自身に対して行われる場合にのみ、本当に価値があります。架空の命令ミックスではなく、独自の命令ミックスです。自分のパフォーマンスを測定します。変える。自分自身と比較して、自分のパフォーマンスが良くなったり悪くなったりするかどうかを確認します。

FLOPS は関係ありません。重要なのは、作業単位あたりの時間です。ハードウェア設計者が期待したベンチマークを実行していないため、ハードウェアの設計パラメーターと一致することはありません。

LINPACK は関係ありません。重要なのは、コード ベースと、パフォーマンスを変更するために行っている変更です。

于 2008-11-30T19:16:55.583 に答える
1

可能な限り高速に実行しようとしますが、特に回避できる関数呼び出しがある場合は、時間を費やしている場所を見つける必要があります。

これは、実行中に数回中断して、何をしているかを確認するという簡単な方法で行います。ここに私が見つけた種類のものがあります:

  • ほとんどの場合、導関数および/またはヤコビアンを計算する過程にあります。exp()この時間の多くは、 、log()、などの数学関数の呼び出しに費やされますsqrt()。多くの場合、これらは同じ引数で繰り返され、メモ化できます。(大幅な高速化)

  • 積分の許容誤差が必要以上に厳しいため、導関数の計算に多くの時間が費やされます。(もっと早く)

  • 方程式が硬いと考えられているために (DLSODE Gear などの) 暗黙的な積分アルゴリズムが使用されている場合、そうではない可能性が高く、Runge-Kutta のようなものを使用できます。(DVERK)。(さらに速い)

  • モデルが線形 (DGPADM) の場合は、行列指数アルゴリズムを使用できる可能性があります。これは、パフォーマンスと精度の両方で大きなメリットがあり、剛性の影響を受けません。(はるかに速い)

  • 呼び出しスタックの上位では、同じ積分がわずかに異なるパラメーターを使用して繰り返し実行され、それらのパラメーターに関する解の前方勾配または中心差分勾配が決定されている可能性があります。微分方程式自体が微分可能である場合、それらの勾配を解析的に取得するか、感度方程式で方程式を拡張することによって取得できる可能性があります。これははるかに高速であるだけでなく、はるかに正確であり、スタックのさらに上位の処理を高速化できます。

スタックの各レベルを最適化するものを見つける機会として見ることができ、スピードアップはさらに加速します。次に、マルチ CPU に移動すると、並列化可能であると仮定すると、独自の乗算係数が提供されるはずです。

FLOP に戻ります。を最大化 しようとすることもできますが、スタックのすべてのレベルで最適化することにより、最小FLOPs / second化することもはるかに便利です。いずれにせよ、それらを測定するだけでは、ほとんど何もわかりません。 FLOPs / run

于 2009-06-12T18:01:05.020 に答える
1

あなたが言ったように、FLOPSは1秒あたりの浮動小数点演算です。たとえば、演算 (2 つの値の加算、減算、乗算、除算など) にちょうど 1 秒かかる場合、パフォーマンスは単純に 1 FLOPS になります。最近の CPU は数 GigaFLOPS、つまり毎秒数十億の浮動小数点演算を容易に達成します。

于 2008-11-30T18:51:37.617 に答える
0

FLOPS の測定はあまり役に立たないと思います。

達成された FLOPS の数は、アルゴリズムが CPU をどれだけビジー状態に保っているかを示しますが、アルゴリズム自体がどれだけうまく機能しているかはわかりません。

プロセッサに同じ数の FLOPS を実行させる 2 つの異なるアルゴリズムを見つけることができますが、一方は半分の時間で目的の結果を提供します。

単位時間あたりに解かれた微分方程式の数 (つまり、アルゴリズムの目的) など、はるかに「高レベル」の統計を見たほうがよいと思います。

一方、達成された FLOPS の数を測定すると、CPU がどれだけビジーであるかがわかるため、アルゴリズムを改善するのに役立つ場合があります。

于 2008-11-30T19:06:07.387 に答える
0

あなたの雇用主は正しいです。
Fortran プログラム (またはその他のプログラム) の有効性を測定する唯一の方法は、標準ベンチマークが存在する場合は、それに対してテストすることです。

また、FLOP については、「1 秒あたりの浮動小数点演算」の略です。ウィキペディアの定義を参照してください。

于 2008-11-30T18:52:19.580 に答える