使用包含类类型作为模板参数的成员
Members with the containing class type as a template argument
我在编译一些代码时遇到了一些问题,这些代码可以很容易地总结为以下代码:
template <typename _Ty>
class Foo
{
public:
using allocator_type = typename _Ty::allocator_type;
};
template <typename _Ty, typename _Alloc = std::allocator<_Ty>>
class Bar
{
public:
using allocator_type = _Alloc;
Foo<Bar<_Ty, _Alloc>> foo;
};
int main(void)
{
Foo<Bar<int>> x;
}
在Visual Studio中编译失败,出现以下错误:
Error 1 error C2079: 'Bar<int,std::allocator<_Ty>>::foo' uses undefined class 'Foo<Bar<int,std::allocator<_Ty>>>' c:usersduncandesktoptesttestmain.cpp 17 1 Test
如果Foo
具有类型_Ty
的成员(出于同样的原因Foo
不能具有类型Foo
的成员),这显然是一个问题,但由于这里不是这种情况,我有点困惑。更让我吃惊的是,如果我将Bar
的foo
成员改为指针,编译器错误就会消失。更疯狂的是,Foo<Bar<_Ty, _Alloc>>
可以用作Bar
成员函数中的局部变量而不会出错。
在标准中是否有任何东西阻止这种使用,或者这是Visual Studio 2013编译器的错误?我目前没有很容易地访问与GCC的编译器来测试它。这种模式似乎是值得遵循的。
你的代码没有编译,因为在模板专门化class Bar<int>
的实例化时,它要求在class Bar<int>
的定义内的具体Bar<int>
对象。这是不允许的,因为当编译器看到Foo<Bar<int>> foo;
时,它对Bar<int>
一无所知(即,模板专门化Bar<int>
的定义不完整)。
你能做的是传递Bar
作为一个指针。要做到这一点,还需要对指针的Foo
进行专门化,如下面的例子所示:
template <typename _Ty>
class Foo
{
public:
using allocator_type = typename _Ty::allocator_type;
};
template <typename T>
class Foo<T*>
{
public:
using allocator_type = typename T::allocator_type;
};
template <typename _Ty, typename _Alloc = std::allocator<_Ty>>
class Bar
{
public:
using allocator_type = _Alloc;
Foo<Bar*> foo;
};
现场演示
或者强制创建模板专门化Bar<int>
,以便编译器事先知道它:
template <typename _Ty>
class Foo
{
public:
using allocator_type = typename _Ty::allocator_type;
};
template <typename _Ty, typename _Alloc = std::allocator<_Ty>>
class Bar
{
public:
using allocator_type = _Alloc;
Foo<Bar> foo;
};
template class Bar<int>; // force create Bar<int>
现场演示
还要记住:
下划线后接大写字母,保留在STL中使用。
Bar
的名字注入到template class Bar
的定义中。因此,在模板定义内部使用Bar<T, Alloc>
或Bar
是相同的。
相关文章:
- 基于另一个成员参数将函数调用从类传递给它的一个成员
- 使用指向成员的指针将成员函数作为参数传递
- 如何将lambda作为模板类的成员函数参数
- 将成员函数指针作为参数传递给模板方法
- c++构造函数成员初始化:传递参数
- 使用带有 ref 参数的成员函数创建线程时出现编译错误
- 如何将成员函数作为回调参数传递给需要"typedef-ed"自由函数指针的函数?
- 模板化检查是否存在带有参数列表的类成员函数?
- 如何将类成员方法的参数列表自动填充写入可变参数?
- 为什么我需要在成员发起器列表中重复基类的模板参数?
- C++向量默认为成员参数
- 将成员函数作为构造函数参数调用时出错 "Variable is not a type name"
- 可变参数模板参数扩展 类型为 std::function 的类成员
- 绑定到可变参数成员函数
- C/C++ 包含点的宏参数(成员访问运算符)
- 将const char * const参数成员分配给新值
- 基于模板参数成员函数参数的模板专用化
- 如何访问可变参数成员
- 可变类参数成员变量的异构存储
- 非模板类中的可变参数成员