为什么我的模板专业化需要匹配 originals 约束?

Neo*_*ana 2 c++ templates constraints c++20

例如,在这段代码中:

#include <iostream>
#include <type_traits>

template<typename T>
requires std::is_same_v<T,int> || std::is_same_v<T,float> || std::is_same_v<T,double>
bool foo(const T& value)
{
    return true;
}

template<>
bool foo<double>(const double& value)
{
    return false;
}


int main()
{
    std::cout << foo(12)    << std::endl;
    std::cout << foo(1.2f)  << std::endl;
    std::cout << foo(1.2)   << std::endl;

    return 0;
}
Run Code Online (Sandbox Code Playgroud)

如果我|| std::is_same_v<T,double>从约束中删除 ,那么第三个输出将无法编译。

但我不明白的是为什么专业化不能自动定义它自己的约束?专业化本身表明T它应该是有效类型,但现在尝试使用约束要求我提前“记录”所有专业化。考虑一个非玩具示例,其中特化做了一些完全不同的事情,如果回退版本无法对特化类型进行操作,那么在约束中列出该特化类型会令人困惑。

在我看来,编译器可以自动将专用类型包含在约束列表中,因为我在想出一个专用类型不会被视为新约束的情况时遇到了麻烦?

我希望有人知道这是编译器的技术限制还是委员会决定这样做的另一个原因。

Nic*_*las 5

模板的显式特化是相对于主模板定义的。没有主模板,专业化就无法存在。它们是该主要模板的替代品。

在模板实例化期间,如果一组模板参数未通过约束测试,则实例化该模板将失败。它正在实例化导致使用显式特化的主模板。如果为这些模板参数实例化主模板失败,那么您也无法获得其专业化。

  • 我本来打算对现已删除的其他答案发表评论,但我会这样表达这个想法:专业化从属于他们的初选。主模板通过指定模板参数的数量/类型/约束来定义模板“覆盖”的类型空间。模板的特化进一步划分了类型空间,为该空间中的不同点分配不同的实现。这些细分/专业化在主要领域“之外”是没有意义的。如已删除的答案所示,您可以“重载”该函数。 (2认同)