c++ - 基于依赖类型的存在重载

标签 c++ c++11 overloading sfinae overload-resolution

我有两个同名的模板函数 (foo)。它们的签名仅在第二个参数的类型上有所不同,这取决于模板参数 T。令我感到惊讶的是,我可以根据 T::AT::B 是否存在类型来使用它来重载。这是标准中专门提供的东西吗(如果是这样,将不胜感激),还是我只是太过拘泥于没有将其识别为基本的重载解决方案?

#include <iostream>
using namespace std;

template<typename T>
void foo(T t, typename T::A* a = 0) {
  cout << "Had an A" << endl;
}

template<typename T>
void foo(T t, typename T::B* b = 0) {
  cout << "Had a B" << endl;
}

struct HasAnAType {
  typedef int A;
};

struct HasABType {
  typedef int B;
};

struct HasAAndBTypes {
  typedef int A;
  typedef int B;
};

int main() {
  HasAnAType a;
  HasABType b;
  HasAAndBTypes ab;

  foo(a);  // prints "Had an A"
  foo(b);  // prints "Had a B"
  foo(ab); // won't compile: 'ambiguous call to overloaded function'
}

作为背景,我在研究 std::enable_shared_from_this 的实现时发现这是可能的,它依赖于这种类型的重载。

最佳答案

感谢SFINAE ,重载 void foo(T t, typename T::B* b = 0)T::B 不存在时被移除存在(类似于 T::A)

所以当两者都可用时,两个重载都是可行的,因此调用是不明确的。

关于c++ - 基于依赖类型的存在重载,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32841952/

相关文章:

c++ - C++11 的 LLVM 和 Clang 支持

c++ - 实用和高级的 C++ 用法

c++ - 是否可以从同一线程移动分配 std::thread 对象

接收 std::vector 作为参数的 C++ 模板函数

c++ - 让某个类的 '=' 运算符在声明时运行构造函数

c# - params 过载明显的歧义 - 仍然可以编译和工作吗?

c++ - 如何使用 CLI 程序获取密码?

c++ - Visual C++ 2008 中的单个文件编译和执行?

c++ - unique_ptr 未使用默认删除器进行初始化

c# - 如果委托(delegate)不能重载,那么 'Func' 和 'Action' 如何有 16 个重载?