C++98 标准说:
[temp.class.spec] 通过名称查找找不到部分特化声明本身。
如果对于显式特化也是如此,这使得类模板显式/部分特化的前向声明不可见。
[temp.class.spec.match] 当在需要类实例化的上下文中使用类模板时,有必要确定是使用主模板还是部分特化生成实例化。
这意味着直到匹配特化的(隐式)实例化点才做出显式/部分特化的选择——这仅在需要完全定义类时发生。
在以下示例中,前向声明的显式特化的唯一影响是使程序无法编译。
namespace N
{
template<class T>
struct S
{
};
typedef S<char> Type; // name lookup finds S<T>
template<>
struct S<char>; // invisible to name lookup
typedef S<char> Type; // name lookup finds S<T>
int f(S<char>*); // name lookup finds S<T>
S<int> object; // implicitly instantiates S<int>
template<>
struct S<int>; // illegal, explicit specialization after instantiation
}
N::S<char>* p = 0; // name lookup finds N::S<T>
int i = f(p); // name lookup finds N::f via ADL
N::S<char> object; // illegal, incomplete type N::S<char>
在这两种情况下,使程序编译的唯一方法(除了删除特化)是在实例化之前为这两种特化提供定义——这使得前向声明有点毫无意义。
这种行为是否有任何实际的实际应用?除此之外,这些前向声明还有什么用处吗?