2017-08-23 13 views
3

簡単な言葉で言えば、C++コンパイラが変数が特定の型であることを証明できれば、仮想関数をインライン化できます。なぜそれが(、MSVC 2017でテスト打ち鳴らす4.0、7.2およびICC 17 GCC)このような場合にはそれを行うことはできません。なぜこの仮想メソッドをインライン化できないのですか?

#include <iostream> 

class Callable { 
public: 
    virtual int sq(int n) const; 
}; 

class Square : public Callable { 
public: 
    inline int sq(int n) const override final { 
     return n*n; 
    } 
}; 

class Call { 
public:  
    const Callable caller; 
}; 

class Methods { 
public: 
    constexpr static const Call c {Square()}; 
}; 

int main() { 
    using std::cout; 
    cout << Methods().c.caller.sq(5); 
} 

私はgodboltで打ち鳴らすの最適化出力(下のリンク)がCallable::sqではないだろうと言っていることに気づきましたその定義が利用できないためインライン化されます。しかし、Methods::cstaticconstです。 Call::callerconstです。また、Square::sqfinalです。私が知る限り、実行時に変更する方法はありません。または私は何かを逃していますか?

一方、コンパイラは、このバージョンで機能をインライン化することができます:

#include <iostream> 

class Callable { 
public: 
    virtual int sq(int n) const; 
}; 

class Square : public Callable { 
public: 
    inline int sq(int n) const override final { 
     return n*n; 
    } 
}; 

class Call { 
public:  
    Callable const* caller; 
}; 

class Methods { 
public: 
    Call c {new Square()}; 
}; 

int main() { 
    using std::cout;  
    cout << Methods().c.caller->sq(5); 
} 

なぜそうでしょうか?簡単に確認できるようにゴッドボルト用Link

+0

「clangの最適化ビュー」とは何ですか? – xaxxon

+0

@ xaxxon私は最適化の出力を意味しました。私はそれを修正します。とにかく、私はコンパイラについてはっきりとは分かりませんが、それはとにかくゴッドボルトの機能です。 「最適化出力を表示する」をクリックして、私が提供したリンクでそれを見ることができます。コンパイラのコードを最適化する手順を示しています。 –

+0

あなたはそれをインラインにすることができないこと、そしてそれをしないことを選んだだけではないことをどうやって知っていますか? "Callable :: sqはその定義が利用できないためインライン化されません"と私はどこでも見ていないよ – xaxxon

答えて

0

仮想関数宣言の最後に{}を追加してみてください。

virtual int sq(int n) const {} 
関連する問題