任何容器的构建都离不开分配器,分配器顾名思义就是分割配置内存资源的组件,分配器的效率直接影响力容器的效率。

operator new()和malloc()

C/C++底层都是通过malloc()调用系统的API来为程序申请内存。

每次申请内存时,malloc()函数实际上会多分配一些空间,这些空间并不能被程序实际使用(例上图分配的size内存上下即为没有被程序使用的overload部分的内存),malloc()申请的内存越大,overload占的比例越小,malloc()申请的内存越小,overload占的比例越大。

这是设计的原因是为了实现malloc的通用性而做的必要牺牲(即申请内存的随机性和大小的不确定性),由于在归还内存时仅仅提供一个指针,所以overload部分记录的是申请的区块内存大小,以便free的时候能够精确地回收内存。

VC6标准的容器默认都是使用allocater作为分配器

从下面的allocator的调用我们可以看出来,allocator实际上就是用operator new()来申请(即用malloc申请)内存

右边圆框圈起来的代码就是直接用allocator申请和释放内存的例程,他通过allocator<int>()产生了一个无名的临时对象,调用其内部的allocate方法申请512个int*类型的空间,然后在归内存时也相同用无名临时对象归还p指针所指的512大小的内存,由于其接口设计总要记住内存大小,所以使用较少。(话说用无名临时对象这种语法也不常见呢,尤其像这种显式的声明)

BC和GCC2.9中实现的allocator基本一致,但是在GCC2.9的代码注释中,它们有说明自己也没有使用自己的allocator,而是使用了SGI。

上面我们提到了,malloc申请内存的弊端,即overload的冗余过多,所以,在STL设计的时候使用的为alloc,这是一种针对STL专门的空间配置器。

由于容器中数据的规整性(例如一个容器确定了数据类型,则其在申请内存时就比较明确),所以alloc设计采用了16长的链表,第0条为8字节,第1条为16字节,第2条为24字节.....第15条为168字节,当容器需要内存时,就从链表中选择合适的一个给它。(虽然这个带内存的链表也是使用malloc申请的内存,但是它已经大大节省了overload,这就是内存池)

然而,在G4.9又使用了operator new的这种低效版本。

分配器——allocators的更多相关文章

  1. STL之分配器allocator

    简单介绍下STL中的分配器allocators. allocators我们一般不会直接接触到,甚至可能并不清楚它的存在,简单的来说,它就是一个幕后工作者,我的印象中它的作用主要在于为容器分配一定的空间 ...

  2. 【STL学习笔记】一、STL体系

    目录 1.标准库以header files形式呈现 2.namespce命名空间 3.STL与OO 4.STL六组件及其关系 5.STL组件例子 6.range-based for statement ...

  3. STL之内存管理

    STL以泛型思维为基础,提供了6大组件:容器(containers).算法(algorithms).迭代器(iterators).仿函数(functors).适配器(adapters).分配器(all ...

  4. Linux内存管理 (5)slab分配器

    专题:Linux内存管理专题 关键词:slab/slub/slob.slab描述符.kmalloc.本地/共享对象缓冲池.slabs_partial/slabs_full/slabs_free.ava ...

  5. 理解 glibc malloc:主流用户态内存分配器实现原理

    https://blog.csdn.net/maokelong95/article/details/51989081 Understanding glibc malloc 修订日志: 2017-03- ...

  6. 侯捷STL学习(三)--分配器测试

    第七节:分配器测试 标准的分配器Allocator,#include<ext/...>都是拓展的 可以用不同的分配器测试同一容器 分配器allocate() & deallocat ...

  7. 内存分配器 (Memory Allocator)

    对于大多数开发人员而言,系统的内存分配就是一个黑盒子,就是几个API的调用.有你就给我,没有我就想别的办法. 来UC前,我就是这样觉得的.实际深入进去时,才发现这个领域里也是百家争鸣.非常热闹.有操作 ...

  8. Slab 分配器

    1.什么是Slab 分配器: 以下摘自维基百科:https://en.wikipedia.org/wiki/Slab_allocation Slab  firstly introduced in ke ...

  9. Allocators与Criterion的相同点及区别

    C++98: 1.相同点: Allocators having the same type were assumed to be equal so that memory allocated by o ...

随机推荐

  1. 设计模式(1-3)-动态代理(WeakCache的运用)

    阅读本篇文章前,请事先阅读 理解Java的强引用.软引用.弱引用和虚引用. 看看什么是强引用.什么是弱引用及它们的用途,很必要!!! 上一节讲到,获取对应的代理类时,首先会从缓存中去拿,若拿不到才会去 ...

  2. 理解前端blob和ArrayBuffer,前端接受文件损坏的问题

    1 downloadTemplate().then(res =>{ 2 3 const data = res.data 4 const url = window.URL.createObject ...

  3. 使用ssh连接到centos7中docker容器

    任务: 使用ssh连接到centos7中docker容器 实验步骤: 实验环境搭建,详情请看上一篇. 因为docker中容器的ip通常来说是和真机以及centos7的ip不属于一个网段,因此直接访问是 ...

  4. Spring Cloud Alibaba 使用Feign进行服务消费

    为什么使用Feign? Feign可以把Rest的请求进行隐藏,伪装成类似SpringMVC的Controller一样.你不用再自己拼接url,拼接参数等等操作,一切都交给Feign去做. 使用Fei ...

  5. airflow redis sentinel

    获取master name subscribe __sentinel__:hello mysql plugin table not found mysqld --initialize-insecure ...

  6. 为什么不直接去Arraylist list = new Arraylist();而是直接通过List list = new ArrayList();使用接口的好处

    ArrayList不是继承List接口,是实现了List接口. 你写成ArrayList arrayList = new ArrayList();这样不会有任何问题.和List list = new ...

  7. (十.7) JDBC(使用IDEA连接数据库)

    写SQL语句: 调出mysqlconsole alt + 8 ok,完毕.

  8. Docker部署 Mysql .Net6等容器

    Centos8安装Docker 1.更新一下yum [root@VM-24-9-centos ~]# yum -y update 2.安装containerd.io # centos8默认使用podm ...

  9. python实现圆检测

    目录: (一)霍夫圆检测原理 (二)代码实现 (一)霍夫圆检测原理 (二)代码实现 1 #霍夫圆检测 2 import cv2 as cv 3 import numpy as np 4 5 def d ...

  10. 从零开始学Kotlin第六课

    Kotlin调用java代码: 1.如果是内部工程的类,直接调用,如果是外部的工程项目按照java的方式将jar包导入进来. 2.实例化java对象 我们之前学java的时候实例化对象是这个样子的. ...