我在這里看到了一個問題的答案。在那里,答案的作者利用了以下事實
例外規范不參與1模板引數推導。
在上面鏈接的答案中,解釋了為什么以下內容無法編譯:
#include <iostream>
template<typename T>
void timer(T a) noexcept(func(T()))
{
std::cout<<"template timer called"<<std::endl;
}
void timer(...)
{
std::cout<<"ordinary timer called"<<std::endl;
}
int main()
{
timer(5);//won't compile
return 0;
}
據說由于例外規范不參與TAD,多載決議選擇了函式模板版本,所以當例外規范在稍后實體化時,程式變得不合格式,我們得到錯誤。
現在我修改了上面的程式,看看我是否正確理解了這個話題。特別是,我添加了decltype(func(T()))作為函式模板版本的回傳型別(如下所示),然后錯誤消失了:
template<typename T>
decltype(func(T())) timer(T a) noexcept(func(T())) //return type added here
{
std::cout<<"template timer called"<<std::endl;
return func(T());//return statement added here
}
void timer(...)
{
std::cout<<"ordinary timer called"<<std::endl;
}
int main()
{
timer(5); //works now?
return 0;
}
我的問題是,為什么當我們將回傳型別添加到如上所示的函式模板時,錯誤就消失了?
PS:我的問題不是關于為什么第一個示例給出錯誤有效,而是為什么修改后的示例沒有給出錯誤。
1這句話來自C 模板:完整指南。
uj5u.com熱心網友回復:
這里因為沒有func,所以在函式模板的回傳型別中替換模板引數時,我們得到替換失敗,并且由于 SFINAE 這個函式模板沒有被添加到集合中。換句話說,它被忽略了。
因此呼叫timer(5);使用普通函式timer,因為它是唯一可行的選項,因為函式模板已被忽略。因此程式編譯并給出輸出:
ordinary timer called
轉載請註明出處,本文鏈接:https://www.uj5u.com/yidong/447272.html
上一篇:在構建電子郵件模板編輯器時如何處理tinyMCE行內模式?
下一篇:如何在類模板中多載函式模板函式?
