2

私が遭遇したこの例を理解していません:

int Multiply(int x, int m){
    return x * m;}

template<int m>
int MultiplyBy(int x){
    return x * m;}

int a,b;
a = Multiply(10,8);
b = MultiplyBy<8>(10);

上記の例では、コンパイラは、シフト操作を使用して 2 のべき乗で乗算できることを認識しているため、テンプレート関数は単純な関数よりも高速です。x*8 は、より高速な x << に置き換えられます。単純な関数の場合、コンパイラは m の値を認識しないため、関数をインライン化できない限り最適化を実行できません。

私が理解しているように、テンプレートが最適化できる理由は、コンパイラがコンパイル時に引数 (8) の値を認識しているのに対し、単純な関数は実行時まで x (または m) の値を認識していないためです。では、単純な関数をインライン化すると、この事実がどのように変わるのでしょうか? インライン化は、引数値の実行時の知識を提供しませんか??

4

2 に答える 2

4

インライン化は、引数値の実行時の知識を提供しませんか??

インライン化自体はそうではありません。ただし、2 番目の引数はコンパイル時の定数であるため、コンパイラはその定数をインライン関数に伝達できます。

最初の引数もコンパイル時の定数であるため、全体

a = Multiply(10,8);

で置き換えることができます

a = 80;

実際、最適化をオンにしたときにコンパイラ (gcc 4.7.2) が行うことはまさにこれです。

于 2013-03-20T18:51:12.090 に答える
2
a = Multiply(10,8);

関数呼び出しを手動でインライン化しましょう。

a = 10 * 8;

もちろん、ここでは 8 はコンパイル時の定数であるため、コンパイラは前述のようにビットシフト最適化を使用できます。ただし、より適切な最適化を実行する可能性が高く、 に置き換えるだけ10 * 8です80。コンパイラは非常にスマートです。 などの定数式を指定すると10 * 8、コンパイル時に結果を計算できます。

あなたがやっていたら、それは違うでしょう:

int x;
std::cin >> x;
a = Multiply(10,x);

Multiplyここでインライン化すると、次のようになります。

int x;
std::cin >> x;
a = 10 * x;

コンパイラはxコンパイル時に の値を認識していないため、これを同じ方法で最適化することはできません。

于 2013-03-20T18:55:23.370 に答える