C++简单实现一个内存池的分配

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/yp18792574062/article/details/76034455
#include<iostream>
#include<malloc.h>
using namespace std;
//C++实现一个简单的内存池
class CMemPool
{
private:
	//链表节点
	typedef struct _Node
	{
		struct _Node* prev;
		struct _Node* next;
	}Node;
	//内存池的首地址
	void* m_pMemBlockAdd;
	//已分配出去的内存节点
	Node* m_pAllocatedMemBlock;
	//未分配出去的内存节点
	Node* m_pFreeMemBlock;
	//内存单元个数
	int m_count;
	//内存单元大小(这里指总大小)
	int m_BlockSize;
public:
	CMemPool(int count = 50, int size = 1024);
	~CMemPool();
	//分配内存
	void* Alloc(int size, bool useMemPool = true);
	//释放内存
	void Free(void* p);
};
CMemPool::CMemPool(int count, int size)
	:m_pMemBlockAdd(NULL), m_pAllocatedMemBlock(NULL), m_pFreeMemBlock(NULL)   //除了内存空间大小,还有加上每个节点的两个指针
	,m_count(count), m_BlockSize(count*(size+sizeof(Node)))
{
	m_pMemBlockAdd = ::malloc(m_BlockSize);

	if (m_pMemBlockAdd != NULL)
	{
		//将所有节点连接起来,刚开始的时候都是空闲的
		for (int i = 0; i<count; i++)    //将所有内存结点链接起来
		{
			//每个节点的起始位置
			Node *pCurUnit = (Node *)((char *)m_pMemBlockAdd + i*(size + sizeof(Node)));

			//这里采用的是头插法,双向单链表,不带头结点
			pCurUnit->prev = NULL;
			pCurUnit->next = m_pFreeMemBlock;

			if (NULL != m_pFreeMemBlock)
			{
				m_pFreeMemBlock->prev = pCurUnit;
			}
			m_pFreeMemBlock = pCurUnit;
		}
	}
}
CMemPool::~CMemPool()
{
	::free(m_pMemBlockAdd);
}
//分配内存
void* CMemPool::Alloc(int size, bool useMemPool)
{
	if (size > m_BlockSize || useMemPool == false || m_pMemBlockAdd == NULL || m_pFreeMemBlock == NULL)
	{
		//内存池中没有空闲的内存了,那么重新给分配内存,就不是从内存池中分配内存了
		return ::malloc(size);
	}
	//内存池中有空闲内存
	Node* r = m_pFreeMemBlock;
	//先从表中取出一个内存单元,放入已分配的内存链表中,并且返回该单元的内存地址
	m_pFreeMemBlock = r->next;
	if (m_pFreeMemBlock == NULL)
	{
		m_pFreeMemBlock->prev = NULL;
	}
	r->next = m_pFreeMemBlock;
	if (m_pAllocatedMemBlock != NULL)
	{
		m_pAllocatedMemBlock->prev = r;
	}
	m_pAllocatedMemBlock = r;
	return (void *)((char *)r + sizeof(Node));
}
//释放内存
void CMemPool::Free(void* p)
{
	//p在内存池分配的内存中间
	if (m_pMemBlockAdd<p && p<(void *)((char *)m_pMemBlockAdd + m_BlockSize))
	{
		Node *pCurUnit = (Node *)((char *)p - sizeof(Node));

		m_pAllocatedMemBlock = pCurUnit->next;  //从已分配链表取出回收的内存单元,放入空闲链表中
		if (NULL != m_pAllocatedMemBlock)
		{
			m_pAllocatedMemBlock->prev = NULL;
		}

		pCurUnit->next = m_pFreeMemBlock;
		if (NULL != m_pFreeMemBlock)
		{
			m_pFreeMemBlock->prev = pCurUnit;
		}

		m_pFreeMemBlock = pCurUnit;
	}
	//如果不是在内存池中分配的直接销毁它
	else
	{
		free(p);
	}
}

猜你喜欢

转载自blog.csdn.net/yp18792574062/article/details/76034455
今日推荐