每个分配器类都必须具有类似于以下内容的接口(interface):
template<class T>
class allocator
{
...
template<class Other>
struct rebind { typedef allocator<Other> other; };
};
使用分配器的类这样做有些多余:template<class T, class Alloc = std::allocator<T> >
class vector { ... };
但是为什么这是必要的呢?换句话说,他们不能说:
template<class T>
class allocator { ... };
template<class T, template<class> class Alloc = std::allocator>
class vector { ... };
哪一种既更优雅,更少冗余,又(在某些类似情况下)更安全?他们为什么要选择
rebind
路由,这也会导致更多的冗余(即您必须说两次T
)?(类似的问题出现在
char_traits
上,其余的问题……尽管它们都没有rebind
,但它们仍然可以从模板模板参数中受益。)编辑:
实际上,它运作良好!
template<unsigned int PoolSize>
struct pool
{
template<class T>
struct allocator
{
T pool[PoolSize];
...
};
};
现在,如果仅以这种方式定义vector
:template<class T, template<class> class Alloc>
class vector { ... };
然后您可以说:typedef vector<int, pool<1>::allocator> int_vector;
这样就可以很好地工作,而无需(多余)说两次int
。而且
rebind
内部的vector
操作将变成Alloc<Other>
而不是Alloc::template rebind<Other>::other
。 最佳答案
带引号的文字来自Foundations of Algorithms in C++11,第1卷,第4章,p。 35:
template <typename T>
struct allocator
{
template <typename U>
using rebind = allocator<U>;
};
sample 用法:
allocator<int>::rebind<char> x;
在C++编程语言,第4版,第34.4.1节,第1页中。 998,注释默认分配器类中的“经典”重新绑定(bind)成员:
template<typename U>
struct rebind { using other = allocator<U>;};
Bjarne Stroustrup写道: