代码没贴全,就少一个锁头文件,可以做设计参考
设计思想就是维护一个空闲链表,没有用的就重新申请,有的话就拿链表的头,使用完又还给空闲链表。
/*
一个分配固定大小内存的内存池,使用链表维护
*/
#pragma once
#include
using namespace std;
#include "../Thread/AutoLock.h"
using namespace Extralib::Thread;
struct Link
{
Link* m_pNext;
};
const int DEFAULT_SIZE = 100;
// T的大小不能小于4个字节
template
class MemoryPool
{
public:
MemoryPool(); // 默认
MemoryPool(int nSize); // 内存池个数
~MemoryPool(); // 析构
T* New(); // 获得一个没有用过的内存
void Delete(T* pBuff); // 释放一个内存
void Recycle();
unsigned int GetAllCount();
unsigned int GetUsedCount();
const char* GetDesc();
private:
void Init();
void CreateMemory();// 分配内存
int m_nAll; // 所有分配的个数,统计使用
int m_nNum; // 当前使用的个数
pthread_mutex_t m_mutex; // 互斥锁
Link* m_pFree; // 空闲列表
set m_MemBlockList; // 所有分配的大的内存块,用于删除
//用于统计计数
int m_delCount;
int m_newCount;
char m_DescBuffer[256];
};
template
MemoryPool::MemoryPool()
{
Init();
}
template
MemoryPool::MemoryPool(int nSize)
{
Init();
AutoLock locker(m_mutex);
for(int i = 0; i < nSize ; ++i)
{
CreateMemory();
}
}
template
void MemoryPool::Init()
{
Debug_Assert(sizeof(T) > sizeof(char*));
pthread_mutex_init(&m_mutex,0);
m_nAll = 0;
m_nNum = 0;
m_pFree = 0;
m_delCount = 0;
m_newCount = 0;
};
template
const char* MemoryPool::GetDesc()
{
AutoLock locker(m_mutex);
sprintf(m_DescBuffer,"(All:%d,Used:%d,NewCount:%d,DelCount:%d)",m_nAll,m_nNum,m_newCount,m_delCount);
return m_DescBuffer;
}
template
MemoryPool::~MemoryPool()
{
set::iterator itor;
for(itor = m_MemBlockList.begin(); itor != m_MemBlockList.end(); ++itor)
{
delete[] (*itor);
}
m_MemBlockList.clear();
}
template< typename T>
void MemoryPool::CreateMemory()
{
int nSize = 1;
// 所有分配的内存快
m_nAll += nSize;
char* pData = new char[nSize * sizeof(T)];
m_MemBlockList.insert(pData);
// 结尾连接到当前
Link* pTail = (Link*)(pData + sizeof(T) * (nSize - 1));
pTail->m_pNext = m_pFree;
// 串起来内存
m_pFree = (Link*)pData;
Link* pNode = m_pFree;
for(int i = 0; i < nSize - 1; ++i)
{
pNode->m_pNext = (Link*)(pData + (sizeof(T) * (i + 1)));
pNode = pNode->m_pNext;
}
}
template< typename T >
T* MemoryPool::New()
{
AutoLock locker(m_mutex);
if( !m_pFree )
{
CreateMemory();
}
if(m_pFree)
{
m_nNum++;
m_newCount ++;
Link* pHead = m_pFree;
m_pFree = m_pFree->m_pNext;
new(pHead)T; //调用对象的构造函数
return (T*)pHead;
}
return 0;
}
template
void MemoryPool::Delete(T* pBuff)
{
AutoLock locker(m_mutex);
m_nNum--;
m_delCount ++;
pBuff->~T();
Link* pLink = (Link*)pBuff;
pLink->m_pNext = m_pFree;
m_pFree = pLink;
}
template
void MemoryPool::Recycle()
{
AutoLock locker(m_mutex);
while(m_pFree)
{
Link* pHead = m_pFree;
m_pFree = m_pFree->m_pNext;
m_MemBlockList.erase((char*)pHead);
m_nAll--;
}
}
template
unsigned int MemoryPool::GetAllCount()
{
AutoLock locker(m_mutex);
return m_nAll;
}
template
unsigned int MemoryPool::GetUsedCount()
{
AutoLock locker(m_mutex);
return m_nNum;
}
Original: https://www.cnblogs.com/byfei/p/14104066.html
Author: byfei
Title: 【C++服务端技术】对象池
原创文章受到原创版权保护。转载请注明出处:https://www.johngo689.com/535130/
转载文章受原作者版权保护。转载请注明原作者出处!