我一直在尋找這個問題在這裏找到Template function overload for type containing a type函數模板重載及編譯器優化
凡OP user2079802爲他/她的問題提供了這個代碼:
我嘗試做以下:
#include <iostream> #include <vector> #include <tuple> template <typename T> void f(T t) { std::cout << "1" << std::endl; } template <typename T, typename V> void f(T<std::tuple<V>> t) { std::cout << "2" << std::endl; } int main() { f(std::list<double>{}); // should use first template f(std::vector<std::tuple<int>>{}); // should use second template }
在C++ 14中這樣做的最簡單方法是什麼?我認爲我可以通過這種方式進行模式匹配,但編譯器不會擁有它。
而且songyuanyao提供這樣的回答:
參數
T
作爲模板的名稱,所以它應該被聲明爲template template parameter模板。例如template <template <typename...> class T, typename V> // ~~~~~~~~~~~~~~~~~~~~~~~~~~~~ void f(T<std::tuple<V>> t) { std::cout << "2" << std::endl; }
這是沒有提供實際上修正編譯錯誤以及代碼沒有正常運行的答案。爲了清楚起見,我正在詢問關於此代碼段的問題。 OP最初嘗試對模板類型進行模式匹配,但對模板模板參數的語法不正確。當我通過我的IDE跑了答案,編譯器&調試器{MSVS 2017年CE}在64位英特爾Windows 7計算機上運行我碰巧注意到它們的主要功能是,在OP的函數調用:
f(std::list<double>{}); f(std::vector<std::tuple<int>>{});
第二個函數調用實際上是調用第一個函數模板而不是第二個。這確實引起了幾個問題:
- 這是由於編譯器優化?
- 這是重載解析的結果嗎?
- 在編譯器的底層實際發生了什麼,它在 選擇使用第二個函數模板?
- 或者這是MSVC編譯器的錯誤嗎?
呃,你會得到輸出「1 2」嗎?或者您是否從調試器中看到的結論得出了「第二個函數調用實際上調用第一個函數模板」的結論? –
@DanielJour我打印的值是'1'而不是'2',因此它調用第一個函數而不是第二個函數。 –
這是MSVC編譯器中的一個錯誤。 –