【发布时间】:2014-09-26 10:30:38
【问题描述】:
我正在尝试实现一个类,该类在内存中后面跟着一个任意类型的数组:
template<class T>
class Buf
{
size_t n;
int refs;
explicit Buf(size_t n) : n(n) { }
// other declarations are here as appropriate
// Followed in memory by:
// T items[n];
};
使用operator new 会很容易:
template<class T>
Buf<T> *make_buf(size_t n)
{
// Assume the caller will take care of constructing the array elements
return new(operator new(sizeof(Buf<T>) + sizeof(T) * n)) Buf<T>(n);
}
template<class T>
void free_buf(Buf<T> *p)
{
// Assume the caller has taken care of destroying the array elements
p->~Buf<T>();
return operator delete(p);
}
template<class T>
T *get_buf_array(Buf<T> *p)
{
return reinterpret_cast<T *>(reinterpret_cast<char *>(p) + sizeof(Buf<T>));
}
但是现在,我如何使用一些符合标准的 allocator SomeAllocator 来实现这一点?
是否保证SomeAllocator::rebind<char>::other::allocate 将返回适合任何类型对象对齐的内存?如果是这样,我是否可以安全地使用某种 char 类型的分配器?如果没有,我是否有其他选择,或者一般分配器不可能完成这项任务? (在最坏的情况下,我想我可以将指针转换为 uintptr_t 并手动对齐它们,但我想知道是否有更好的方法。)
【问题讨论】:
-
您可以随时请求更多内存,然后使用
std::align... -
@KerrekSB:哇,太好了。我不知道该功能存在...
-
@KerrekSB:我想问题仍然存在:最好的方法是什么,是否有必要调用该函数?我应该使用 char 的分配器还是 T 的分配器?等
-
它必须是
char的分配器,因为您实际上没有任何可以分配的类型 - 您只需要原始内存。 (不过,它应该是std::allocator_traits<Alloc>::rebind_alloc<char>,而特征应该是rebind_traits......你需要通过特征调用allocate并获得一个本机指针等等。) -
Buf<T>的分配器以该类型的倍数分配,所以我认为这没有用。当然,您可以进行一些大小计算,但至少您仍然需要以某种方式对齐第一个数组元素的地址。
标签: c++ memory-management allocator heterogeneous