为什么C++17中访问模板类constexpr静态成员时自动模板推导不生效?
问题解答
你对C++17类模板参数推导(CTAD)的理解疏漏在于CTAD的生效范围仅局限于类模板实例化对象的构造场景,并不能覆盖所有用到类模板名的场景:
- 写
A a;时属于对象构造语境,CTAD会触发,编译器结合你给的默认模板参数T=int,自动推导出完整类型为A<int>,因此编译通过。 - 访问静态成员的场景不属于CTAD的生效范围:
A本身是类模板的名称,不是一个完整的已实例化类型,哪怕设置了默认模板参数,你也必须显式加尖括号<>来告诉编译器使用默认参数完成实例化,得到完整类型A<int>后才能访问其静态成员。所以A<>::b是合法写法,而A::b直接将模板名当做已实例化的类型使用,不符合C++语法规则,因此编译报错。
补充说明:哪怕静态成员
b完全不依赖模板参数T,这个规则也不会例外。因为类模板的所有成员(包括静态成员)都归属于实例化后的具体类,而非模板本身,模板只是生成具体类的“模板”,本身不持有静态成员。
内容的提问来源于stack exchange,提问作者Fantastic Mr Fox
相关产品推荐
相关产品推荐

