首頁 >後端開發 >C++ >為什麼參數依賴查找 (ADL) 在明確實例化函數範本時失敗?

為什麼參數依賴查找 (ADL) 在明確實例化函數範本時失敗?

DDD
DDD原創
2024-12-11 04:20:10617瀏覽

Why Does Argument Dependent Lookup (ADL) Fail with Explicitly Instantiated Function Templates?

ADL 和函數範本查找

函數範本在 C 程式設計中發揮重要作用,可實現程式碼重複使用和通用功能。但是,當使用參數依賴查找 (ADL) 在特定命名空間中尋找函數範本時,會出現一個微妙的限制。

嘗試使用顯式模板參數呼叫函數模板時,該問題就會顯現出來,如以下程式碼所示snippet:

namespace ns {
    struct foo {};
    template<int i> void frob(foo const&amp;) {}
    void non_template(foo const&amp;) {}
}

int main() {
    ns::foo f;
    non_template(f); // This is fine.
    frob<0>(f); // This is not.
}

此失敗背後的原因源自於C 標準中的特定條款。根據 C 標準 03 14.8.1.6,在使用明確模板參數呼叫函數模板時,ADL 不適用,除非具有該名稱的函數模板在呼叫時可見。

在上面的範例中,有當 frob(f); 時,目前作用域中沒有可見的名為 frob 的函數範本稱為。因此,ADL 不會被觸發,編譯器無法找到所需的函數模板。

為了規避此限制,可以在函數模板之前明確指定命名空間,如下所示:

ns::frob<0>(f);

在這種情況下,ADL 不是必需的,因為函數模板是直接從包含的命名空間呼叫的。

以下程式碼範例進一步說明了 ADL 與函數的行為templates:

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
}

在這個例子中,函數模板 f 在命名空間 A 和 C 中都被定義。建立完成後,編譯器首先檢查目前作用域,發現沒有可見的 f 模板。然後套用 ADL,但由於 f 是非限定名稱,因此它無法在其他命名空間中找到函數模板。

要從命名空間 C 呼叫模板,必須使用 C::f 或 using 指令明確限定名稱如程式碼所示。

以上是為什麼參數依賴查找 (ADL) 在明確實例化函數範本時失敗?的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn