飽くなき高速化への道(演算編) ここにある情報は、私が個人的に調査した結果です。 これらに関して、HSPの著作者である おにたまさんに質問等をなさらないようにお願い致します。m(_ _)m |
ここで行っている高速化は、
実際には微々たる物です。
実践しても、あまり効果は実感できないかもしれません。
すんごい効果が出たという方はご報告を。
a+ より、a++ の方が速いんですよ。1割も。
変数の加減算に a+ a- を使っている部分を
a++ a-- に変換するだけで、その部分を10%も高速化できます。
あと、これは正式な表記では無いのかもしれませんが、
a+=x を、a+x に書きかえるだけで、さらに5%弱の
高速化が図れます。これは結構大きいです。
ループ内部で「5回以上」配列参照を行っている変数は
dup 命令を使って複製した方が、配列参照が無い分実行速度が速くなります。
参照回数が多いほど、元と比べて高速になります。
- 無駄な演算をしない!
if 文の中などで、16+64+128 とか、やっていませんか?
HSPコンパイラは定数計算式の最適化を行っていませんので、
こういった記述は速度低下の原因になります。
ちなみに上の式は、単に 208 と書くのに比べて
5〜6倍ほどの時間を消費するようです。
- 無駄な括弧は使わない!
表を見てもわかるように、括弧は結構時間を食います。
括弧を使わずに済む場所は、括弧を取ってみましょう。
とりあえず、よく使う代入命令関係のベンチマークを取ってみました。
変数の単独操作に関して、非常に興味深い結果が出ています。
- 表中の記号の意味
- n : 定数です。1や2などの数が入ります。
- a x y : 変数です。変数名が入ります。
- 所要時間 : 同一処理を100万回ループしてかかった時間です。
変数 a を単独変更 | 変数 a に代入 | その他 | |||
---|---|---|---|---|---|
命令文 | 所要時間 | 命令文 | 所要時間 | 命令文 | 所要時間 |
a+ | 688 | n | 1075 | dup x,y | 760 |
a++ | 625 | !n | 1344 | gosub * | 890 |
a- | 690 | n{+-*}n | 1435 | continue | 715 |
a-- | 630 | n/n | 1515 | timer | 1220 |
a+=n | 1105 | n{&^}n | 1435 | ||
a+n | 1050 | n|n | 1550 | ||
n{<=>!}n | 1445 | ||||
x.n+y.n | 2100 | ||||
(n+n) | 1880 | ||||
((n+n)) | 2400 | ←括弧遅いです |
|||
(n+n)+n | 2290 | ||||
((n+n)+n) | 2805 | ←やっぱり遅いです |
各操作で追加される時間
命令 | 追加時間 | 備考(命令の説明等) |
---|---|---|
変数参照 1回 | 25 | 表中の n を変数(x y等)に置き換えること |
配列参照 1回 | 280 | ピリオドで配列要素を指定すること |
NOT(単体否定) | 275 | !8 とか。 |
比較 1回 | 375 | 1>0 とか。 |
括弧 1組 | 515 | ( ) のセット |
演算子 1つ | 355 | + - * / & | ^ |
割り算 1回 | 80 | 演算子分も加えます。 |
OR演算 1回 | 115 | 演算子分も加えます。 |
変数代入 1回 | 775 | 結果の変数への代入 |
空ループテストの結果:HSP 2.4h では 280[ms] でしたが、
最新βでは 270[ms] と、約5%の高速化が図られています。
さらに演算関連の命令も2〜4%程度速くなっていました。
さすがはアセンブラの威力って感じですかぁ。