我在看 Effective C++ 第四十二条,它指出 C++ 在解析嵌套从属名称(nested dependent name)时并不会优先假定它是「类型」,于是得显式地在所有嵌套从属类型名称前统统加上 typename, 以声明它是嵌套从属类型名称(nested dependent type name)。但是这 typename 不能用在成员初始化列表(member initialization list)里。问题来了:
假定 varialble_ 是 Base<T> 的数据成员,类型为 int. 那么
template<typename T>
class Derived: public Base<T> {
public:
explicit Derived(int x) : Base<T>::variable_(x) {}
}
按照 C++ 的解析规则,Base<T>::variable_ 应该会被优先解析成非类型的名称,即 Base<T> 的一个数据成员,从而在 Derived 构造函数里被初始化成 x.
但是这么一来,假定 Base<T>::Nested是一种 class, 则
template<typename T>
class Derived: public Base<T> {
public:
explicit Derived(int x) : Base<T>::Nested(x) {}
private:
int second_variable_;
}
怎么还能保证 Base<T>::Nested(x) 会调用 Base<T>::Nested(int x) 构造函数来初始化其类对象,而不是把 Base<T>::Nested 当成一种 Base<T> 的数据成员呢?
Copyright 2014-2025 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号
我突然发现我把
Base<T>::Nested(x)和Base<T>的构造函数搞混了。Derived作为派生类,只能在成员初始化列表内,调用基类Base<T>的构造函数,以及初始化它自己的数据成员。如果
Derived继承Base<T>::Nested, 其实这就意味着Base<T>::Nested是一个类,编译器会知道成员初始化列表里Base<T>::Nested(int x)是一个构造函数的。其实 Effective C++ 第四十二条也指出了 C++ 禁止在 base class lists 用typename, 毕竟本来就画蛇添足。话说回来,在成员初始化列表内,要把
Base<T>::variable_解析成一个类型,也没有意义。