首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >为什么函数模板不允许使用私有类型的显式专门化?

问为什么函数模板不允许使用私有类型的显式专门化?
EN

Stack Overflow用户
提问于 2022-05-15 18:51:06
回答 1查看 964关注 0票数 13

https://godbolt.org/z/s5Yh8e6b8

我不明白这背后的原因:为什么使用私有类型的显式专门化允许类模板,而不允许函数模板?

假设我们有一堂课:

代码语言:javascript
复制
class pepe
{
    struct lolo
    {
        std::string name = "lolo";
    };
public:
    static lolo get()
    {
        return {};
    }
};
  • 类模板可以显式地专门化。
  • 函数模板在隐式实例化方面没有问题。
  • 虽然您不能创建spec_class<pepe::lolo>{},因为pepe::lolo是不可访问的。
代码语言:javascript
复制
template <typename>
struct spec_class
{};

// this is ok
template <>
struct spec_class<pepe::lolo>
{};

// this will be ok also upon implicit instantiation
template <typename T>
void template_func(const T &t)
{
    std::cout << "implicit: " << t.name << std::endl;
}

但是:

代码语言:javascript
复制
// this is not ok!
// template <>
// void template_func(const pepe::lolo &p)
// {
//     std::cout << "explicit: " << p.name << std::endl;
// }

// this is ok, but more or less understandable why
template <>
void template_func(const decltype(pepe::get()) &p)
{
    std::cout << "explicit: " << p.name << std::endl;
}

// not ok, but expected
// void func(const pepe::lolo&)
// {}

那么:为什么禁止函数模板的显式专门化?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2022-05-15 22:06:49

在C++20中,由于PR0692,在函数模板的专门化参数中使用私有成员是完全有效的。特别是,在temp.spec.general#6中添加了以下措辞

通常的访问检查规则不适用于显式实例化或显式专门化的声明中的名称,但出现在函数体、默认参数、基子句、成员规范、枚举器列表或静态数据成员或变量模板初始化器中的名称除外。 注意1:特别是,函数声明器中使用的模板参数和名称(包括参数类型、返回类型和异常规范)可以是通常无法访问的私有类型或对象。-尾注

(强调地雷)

没有编译的代码是GCC虫97942造成的,它在Clang中编译得很好。演示。

票数 19
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/72251287

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档