為什么ADL沒有找到功能模板?C ++規范的哪一部分限制參數依賴查找在相關命名空間集合中查找函數模板?換句話說,為什么main下面的最后一次調用無法編譯?namespace ns { struct foo {}; template<int i> void frob(foo const&) {} void non_template(foo const&) {}}int main() { ns::foo f; non_template(f); // This is fine. frob<0>(f); // This is not.}
3 回答
慕的地10843
TA貢獻1785條經驗 獲得超8個贊
這部分解釋了它:
C ++標準03 14.8.1.6:
[注意:對于簡單的函數名稱,即使函數名稱在調用范圍內不可見,依賴于參數的查找(3.4.2)也適用。這是因為調用仍然具有函數調用的語法形式(3.4.1)。但是當使用帶有顯式模板參數的函數模板時,除非在調用點處有一個具有該名稱的函數模板,否則調用沒有正確的語法形式。如果看不到這樣的名稱,則調用語法不完善,并且參數依賴查找不適用。如果某些此類名稱可見,則應用依賴于參數的查找,并且可以在其他名稱空間中找到其他函數模板。
namespace A {
struct B { };
template<int X> void f(B);}namespace C {
template<class T> void f(T t);}void g(A::B b) {
f<3>(b); //ill-formed: not a function call
A::f<3>(b); //well-formed
C::f<3>(b); //ill-formed; argument dependent lookup
// applies only to unqualified names
using C::f;
f<3>(b); //well-formed because C::f is visible; then
// A::f is found by argument dependent lookup}
慕尼黑8549860
TA貢獻1818條經驗 獲得超11個贊
從c ++ 20開始,adl與顯式函數模板一起工作也很好。以下是提議: P0846R0:不可見的ADL和功能模板:
不要求用戶使用template關鍵字,而是建議對查找規則進行修訂,以便正常查找產生無結果或找到一個或多個函數且后面跟aa“<”的名稱將被視為如果找到了函數模板名稱并且將導致執行ADL。
目前,只有GCC 9實現了此功能,因此您的示例可以編譯。
live demo。
- 3 回答
- 0 關注
- 380 瀏覽
添加回答
舉報
0/150
提交
取消
