欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

tinystl实现(第一步:alloc.h)

程序员文章站 2022-05-24 20:49:51
...

经过长时间的学习终于可以开始tinystl的仿(chao)写工作了,本文参考了这位大佬的github,坦白讲我只是补充了注释,因为tinystl的代码真的非常经典而我又没什么这种大型项目的经验,所以只能这样做,不过相信能够有助于大家的学习
alloc.h文件是项目的开始部分,无论是哪一个容器,都需要分配内存才能行动,alloc.h文件也是内存分配中的最基石,接下来让我们看代码

#pragma once
#ifndef _ALLOC_H_
#define _ALLOC_H_
#include<cstdlib>
namespace mySTL {
	class alloc {
	private:
		enum EAlign{ALIGN = 8};//小型区块的上调边界
		enum EMaxBytes{MAXBYTES=128};//上限,超过此大小直接使用malloc更佳
		enum ENFreeLists{NFREELISTS=(EMaxBytes::MAXBYTES/EAlign::ALIGN) };//有多少个区块,就要有多少freelist来保证其回收
		enum ENObjs{NOBJS=20};//每次增添的节点数
	private:
		//freelists的节点构造
		union obj {//利用union节省了空间,这个区块既可以放下一块的指针,又可以存放数据
			union obj *next;
			char client[1];
		};
		static obj *free_list[ENFreeLists::NFREELISTS];//此处调用了上方的宏,只所以使用静态是为了让这部分唯一(不唯一则不安全)
	private:
		static char *start_free;//内存池的起始位置
		static char *end_free;//内存池的结束位置
		static size_t heap_size;//堆的大小
		//之所以在这里使用静态内存的原因也很清楚,这些数据都是唯一的,不可能同时存在两个,一旦改变(一般也不改变)就是全局一起改变
	private:
		//将byte上调至8的倍数
		static size_t ROUND_UP(size_t bytes) {
			return ((bytes + EAlign::ALIGN - 1) / EAlign::ALIGN);
		}
		//根据区块大小,决定使用第n号free-list,n从0开始计算
		static size_t FREELIST_INDEX(size_t bytes) {
			return (((bytes)+EAlign::ALIGN - 1) / EAlign::ALIGN - 1);
		}
		static void *refill(size_t n);
		
		//配置一大块空间,可容纳nobjs个大小为size的区块
		//如果配置nobjs个区块有所不便(其实就是没有这么多连续内存拿的出来),nojbs可能会降低
		static char *chunk_alloc(size_t size, size_t& nojbs);
	public:
		//外部可以调用的部分
		static void *allocate(size_t bytes);
		static void deallocate(void *ptr, size_t bytes);
		static void *reallacate(void *ptr, size_t old_sz, size_t new_sz);
	};//静态方法效率上比实例化要高,这种经常要用的函数静态是最好了,每次实例化都要成本



}
#endif