3
我用簡單的語言讀到,如果C++編譯器可以證明變量是某種類型的,它可以內聯虛函數。爲什麼不能做到這一點在這種情況下(與MSVC 2017年進行測試,鐺4.0,GCC 7.2和ICC 17):爲什麼不能將這種虛擬方法內聯?
#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::c
是static
和const
。 Call::caller
也是const
。另外,Square::sq
是final
。據我所知,他們不會在運行時改變方式。或者我錯過了什麼?
在另一方面,編譯器能夠內聯函數在這個版本:
#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爲godbolt爲便於檢查。
什麼是「鏗鏘的優化視圖」? – xaxxon
@xaxxon我的意思是優化輸出。我會解決它。我不確定關於鏗鏘聲,特別是編譯器,但它是godbolt的一個特性。你可以在我提供的鏈接中看到它,點擊「顯示優化輸出」。它顯示了編譯器嘗試優化代碼的步驟。 –
你怎麼知道叮噹不能內聯它,它不只是選擇不?你在哪裏看到它說:「Callable :: sq不會被內聯,因爲它的定義是不可用的」我沒有看到任何地方 – xaxxon