我想在内存管理器中成功分配一个数组。我很难在Heap中成功完成数据设置。我不知道如何实例化数组的元素,然后设置传入该数组的指针。 非常感谢任何帮助。 =)
基本上总结一下,我想使用自己的Heap块而不是普通的堆来编写自己的新[#]函数。甚至不想考虑动态阵列需要什么。的 o.O
// Parameter 1: Pointer that you want to pointer to the Array.
// Parameter 2: Amount of Array Elements requested.
// Return: true if Allocation was successful, false if it failed.
template <typename T>
bool AllocateArray(T*& data, unsigned int count)
{
if((m_Heap.m_Pool == nullptr) || count <= 0)
return false;
unsigned int allocSize = sizeof(T)*count;
// If we have an array, pad an extra 16 bytes so that it will start the data on a 16 byte boundary and have room to store
// the number of items allocated within this pad space, and the size of the original data type so in a delete call we can move
// the pointer by the appropriate size and call a destructor(potentially a base class destructor) on each element in the array
allocSize += 16;
unsigned int* mem = (unsigned int*)(m_Heap.Allocate(allocSize));
if(!mem)
{
return false;
}
mem[2] = count;
mem[3] = sizeof(T);
T* iter = (T*)(&(mem[4]));
data = iter;
iter++;
for(unsigned int i = 0; i < count; ++i,++iter)
{
// I have tried a bunch of stuff, not sure what to do. :(
}
return true;
}
堆分配功能:
void* Heap::Allocate(unsigned int allocSize)
{
Header* HeadPtr = FindBlock(allocSize);
Footer* FootPtr = (Footer*)HeadPtr;
FootPtr = (Footer*)((char*)FootPtr + (HeadPtr->size + sizeof(Header)));
// Right Split Free Memory if there is enough to make another block.
if((HeadPtr->size - allocSize) >= MINBLOCKSIZE)
{
// Create the Header for the Allocated Block and Update it's Footer
Header* NewHead = (Header*)FootPtr;
NewHead = (Header*)((char*)NewHead - (allocSize + sizeof(Header)));
NewHead->size = allocSize;
NewHead->next = NewHead;
NewHead->prev = NewHead;
FootPtr->size = NewHead->size;
// Create the Footer for the remaining Free Block and update it's size
Footer* NewFoot = (Footer*)NewHead;
NewFoot = (Footer*)((char*)NewFoot - sizeof(Footer));
HeadPtr->size -= (allocSize + HEADANDFOOTSIZE);
NewFoot->size = HeadPtr->size;
// Turn new Header and Old Footer High Bits On
(NewHead->size |= (1 << 31));
(FootPtr->size |= (1 << 31));
// Return actual allocated memory's location
void* MemAddress = NewHead;
MemAddress = ((char*)MemAddress + sizeof(Header));
m_PoolSizeTotal = HeadPtr->size;
return MemAddress;
}
else
{
// Updating descriptors
HeadPtr->prev->next = HeadPtr->next;
HeadPtr->next->prev = HeadPtr->prev;
HeadPtr->next = NULL;
HeadPtr->prev = NULL;
// Turning Header and Footer High Bits On
(HeadPtr->size |= (1 << 31));
(FootPtr->size |= (1 << 31));
// Return actual allocated memory's location
void* MemAddress = HeadPtr;
MemAddress = ((char*)MemAddress + sizeof(Header));
m_PoolSizeTotal = HeadPtr->size;
return MemAddress;
}
}
Main.cpp的
int* TestArray;
MemoryManager::GetInstance()->CreateHeap(1); // Allocates 1MB
MemoryManager::GetInstance()->AllocateArray(TestArray, 3);
MemoryManager::GetInstance()->DeallocateArray(TestArray);
MemoryManager::GetInstance()->DestroyHeap();
答案 0 :(得分:0)
至于这两个具体要点:
对于(1):在C ++中没有“初始化”数组元素的明确概念。至少有两种合理的行为,这取决于你想要的语义。第一种是简单地将数组归零(参见memset)。另一种方法是为数组的每个元素调用默认构造函数 - 我不建议使用此选项,因为默认(零参数)构造函数可能不存在。
编辑:使用inplace-new初始化的示例
for (i = 0; i < len; i++)
new (&arr[i]) T();
For(2):“你的意思并不完全清楚”,然后设置传入该数组的指针。您可以“设置”返回的内存为data = static_cast<T*>(&mem[4])
,您已经这样做了。
其他一些警告(编写自己的内存管理器),要非常小心字节对齐(reinterpret_cast(mem)%16);你需要确保你返回的是单词(甚至是16字节)对齐的点。另外,我建议使用inttypes.h明确使用uint64_t来明确大小 - 当前看起来这个分配器会因> 4GB分配而中断。
编辑: 从实验说起 - 编写内存分配器是一件非常困难的事情,调试起来更加痛苦。正如评论者所说,内存分配器是特定于内核的 - 因此有关您的平台的信息将非常有用。