STL源码剖析(一)allocator内存分配类

内存分配器allocator

1,内存分配器隐藏在容器背后工作,STL的操作对象存放在容器内,而容器需要配置一定的空间。
2,空间不一定是内存,可以是磁盘或其他辅助存储介质,但一般情况下allocator配置对象为内存。
3,内存配置操作由allocate()负责,内存释放操作由deallocate()负责;对象构造操作由construct()负责,对象析构操作由destory()负责。
4,C++本身不直接支持指针所指对象的类型判断,也不支持对象析构函数是否为trivial的判断,value_type()和__type_traits<>如何实现后续详解。

allocator模板类定义如下:

namespace std _GLIBCXX_VISIBILITY(default)
{
  template<typename _Tp> //模板类allocator<_Tp>
    class allocator : public __allocator_base<_Tp>
    {
   public: //类型定义,__alloc_traits中详细介绍
      typedef size_t     size_type;
      typedef ptrdiff_t  difference_type; //元素之间的距离
      typedef _Tp*       pointer; //指针类型
      typedef const _Tp* const_pointer;
      typedef _Tp&       reference; //左值引用类型
      typedef const _Tp& const_reference;
      typedef _Tp        value_type; //元素类型

      template<typename _Tp1> //重绑定,获得_Tp1的内存分配器allocator<_Tp1>
	  struct rebind //重新绑定模板类型_Tp1并将allocator<_Tp1>重命名为other
	  { typedef allocator<_Tp1> other; };

      typedef true_type propagate_on_container_move_assignment;
      typedef true_type is_always_equal;

      allocator() throw() { } //默认构造函数
      allocator(const allocator& __a) throw()
      : __allocator_base<_Tp>(__a) { } //拷贝构造函数
	  
      template<typename _Tp1> //泛化的拷贝构造函数
	  allocator(const allocator<_Tp1>&) throw() { }
	  
      ~allocator() throw() { } //默认析构函数
	};
	
  template<>
    class allocator<void> //模板类allocator的特例化版本allocator<void>
    {
    public:
      typedef size_t      size_type;
      typedef ptrdiff_t   difference_type;
      typedef void*       pointer;
      typedef const void* const_pointer;
      typedef void        value_type;

      template<typename _Tp1>
	  struct rebind
	  { typedef allocator<_Tp1> other; };

      typedef true_type propagate_on_container_move_assignment;
      typedef true_type is_always_equal;

      template<typename _Up, typename... _Args> //对象构造,使用可变参数_Args
	  void
	  construct(_Up* __p, _Args&&... __args) //参数args构造_Up对象,forward转发保持参数左右值属性及const属性
	  { ::new((void *)__p) _Up(std::forward<_Args>(__args)...); }

      template<typename _Up>
	  void
	  destroy(_Up* __p) { __p->~_Up(); } //对象析构,调用_Up析构函数完成析构操作
    };
}

继承自__allocator_base如下:

namespace std
{
  template<typename _Tp>
    using __allocator_base = __gnu_cxx::new_allocator<_Tp>;
}

namespace __gnu_cxx _GLIBCXX_VISIBILITY(default)
{ 
  //使用std中size_t和ptrdiff_t定义,为了程序的可移值性适应不同平台
  using std::size_t; //表unsigned类型大小
  using std::ptrdiff_t; //表两指针之间距离

  template<typename _Tp>
    class new_allocator
    {
    public: //类型定义,后续__alloc_traits中详细介绍
      typedef size_t     size_type;
      typedef ptrdiff_t  difference_type; //元素之间的距离
      typedef _Tp*       pointer; //指针类型
      typedef const _Tp* const_pointer;
      typedef _Tp&       reference; //左值引用类型
      typedef const _Tp& const_reference;
      typedef _Tp        value_type; //元素类型

      template<typename _Tp1>
	  struct rebind //重绑定,在当前内存分配类型_Tp中定义另一类型_Tp1的内存分配
	  { typedef new_allocator<_Tp1> other; }; //另一类型的内存分配命名为other

      typedef std::true_type propagate_on_container_move_assignment;
	  
      new_allocator() _GLIBCXX_USE_NOEXCEPT { } //默认构造函数
      new_allocator(const new_allocator&) _GLIBCXX_USE_NOEXCEPT { } //拷贝构造函数
	  
      template<typename _Tp1> //构造函数模板,泛化的拷贝操作
	  new_allocator(const new_allocator<_Tp1>&) _GLIBCXX_USE_NOEXCEPT { }
	  
      ~new_allocator() _GLIBCXX_USE_NOEXCEPT { } //默认析构函数
	  
      pointer //返回指向对象__x的指针,算式a.address(x)等同于&x
      address(reference __x) const _GLIBCXX_NOEXCEPT
      { return std::__addressof(__x); } //std::__addressof()获取左值表达式的地址
	  
      const_pointer //返回指向对象的const指针
      address(const_reference __x) const _GLIBCXX_NOEXCEPT
      { return std::__addressof(__x); }

      pointer //配置内存空间,返回n个Tp类型内存空间,_n允许为0
      allocate(size_type __n, const void* = static_cast<const void*>(0))
      {
		if (__n > this->max_size()) //检查可最大配置内存空间
	  		std::__throw_bad_alloc();
		return static_cast<_Tp*>(::operator new(__n * sizeof(_Tp))); //封装::operator new分配内存空间
      }

      void //释放已配置空间
      deallocate(pointer __p, size_type) // __p不允许为空指针.
      {
		::operator delete(__p); //封装::operator delete释放内存
      }
	 
      size_type //返回可成功配置的最大值
      max_size() const _GLIBCXX_USE_NOEXCEPT
      { return size_t(-1) / sizeof(_Tp); }
	  
      template<typename _Up, typename... _Args> //泛化的对象构造操作,使用可变参数_Args
	  void //参数args构造_Up对象,forward转发保持参数左右值属性及const属性
	  construct(_Up* __p, _Args&&... __args)
	  { ::new((void *)__p) _Up(std::forward<_Args>(__args)...); }

      template<typename _Up> //析构函数模板,泛化的对象析构操作,调用对象__p的析构函数
	  void
	  destroy(_Up* __p) { __p->~_Up(); } //调用_Up析构函数完成析构操作
    };
  //内存分配类中重载的运算符
  template<typename _Tp> //重载==运算符,相等时返回true
    inline bool
    operator==(const new_allocator<_Tp>&, const new_allocator<_Tp>&)
    { return true; }

  template<typename _Tp> //重载!=运算符,不等时返回false
    inline bool
    operator!=(const new_allocator<_Tp>&, const new_allocator<_Tp>&)
    { return false; }
} // namespace

构造和析构基本工具:construct()和destory()

namespace std _GLIBCXX_VISIBILITY(default)
{
  template<typename _T1, typename... _Args> //构造函数模板,模板参数为对象类型和对象所需参数
    inline void //构造对象__p,forward转发保持__args参数属性
    _Construct(_T1* __p, _Args&&... __args)
    { ::new(static_cast<void*>(__p)) _T1(std::forward<_Args>(__args)...); }

  template<typename _T1> //拷贝构造函数模板,模板参数为对象类型
    inline void //拷贝对象
    _Construct_novalue(_T1* __p)
    { ::new(static_cast<void*>(__p)) _T1; }

  template<typename _Tp> //析构函数模板,模板参数为对象类型
    inline void //对象析构,接受一个指针,将指针所指对象析构
    _Destroy(_Tp* __pointer)
    { __pointer->~_Tp(); }

  template<bool> //模板类 _Destroy_aux<bool>
    struct _Destroy_aux
    {
      template<typename _ForwardIterator>
        static void //析构迭代器范围内所有元素
        __destroy(_ForwardIterator __first, _ForwardIterator __last)
		{
		  for (; __first != __last; ++__first) //for循环,调用_Destroy析构对象
		    std::_Destroy(std::__addressof(*__first));
		}
    };
 
  template<> //模板类 _Destroy_aux的特例化版本 _Destroy_aux<true>
    struct _Destroy_aux<true>
    {
      template<typename _ForwardIterator>
        static void
        __destroy(_ForwardIterator, _ForwardIterator) { }
    };

  template<typename _ForwardIterator> //模板类_Destroy<_ForwardIterator>
    inline void //析构[first, last)范围内所有对象
    _Destroy(_ForwardIterator __first, _ForwardIterator __last)
    { //如果destructor为trivial,不需要一次次调用析构函数
      typedef typename iterator_traits<_ForwardIterator>::value_type
                       _Value_type; //获取迭代器_ForwardIterator所指对象类型
      static_assert(is_destructible<_Value_type>::value,
		    "value type is destructible");
	  //__has_trivial_destructor(_Value_type)判断该类型析构函数是否trivial
	  //__type_traits提取类型特性,判断存在默认构造函数、拷贝构造函数、赋值操作、析构函数
	  //如果存在则可使用对应函数完成构造、拷贝、赋值、析构操作,如果不存在则需要采用内存直接操作
	  //若为true,std::_Destroy_aux<true>::__destroy(__first, __last)
	  //若为false,循环整个范围,每个对象调用std::_Destroy(std::__addressof(*__first))
      std::_Destroy_aux<__has_trivial_destructor(_Value_type)>::
	  __destroy(__first, __last);
    }

  template<bool> //模板类 _Destroy_aux<bool>
    struct _Destroy_n_aux
    {
      template<typename _ForwardIterator, typename _Size>
        static _ForwardIterator //析构迭代器__first开始的__count个元素
        __destroy_n(_ForwardIterator __first, _Size __count)
		{
		  for (; __count > 0; (void)++__first, --__count)
		    std::_Destroy(std::__addressof(*__first));
		  return __first;
		}
    };
 
  template<> //模板类的特例化版本_Destroy_aux<true>
    struct _Destroy_n_aux<true>
    {
      template<typename _ForwardIterator, typename _Size>
        static _ForwardIterator
        __destroy_n(_ForwardIterator __first, _Size __count)
		{
		  std::advance(__first, __count);
		  return __first;
		}
    };

  template<typename _ForwardIterator, typename _Size> //函数模板
    inline _ForwardIterator //析构迭代器__first开始的__count个元素
    _Destroy_n(_ForwardIterator __first, _Size __count)
    {
      typedef typename iterator_traits<_ForwardIterator>::value_type
                       _Value_type; //迭代器所指元素类型
      static_assert(is_destructible<_Value_type>::value,
		    "value type is destructible");
      //根据对象是否有析构函数,调用模板类_Destroy_n_aux<bool>下__destroy_n函数
      return std::_Destroy_n_aux<__has_trivial_destructor(_Value_type)>::
	  __destroy_n(__first, __count);
    }

  template<typename _ForwardIterator, typename _Allocator> //析构函数模板,模板参数为迭代器类型和内存分配器
    void //可使用自定义内存分配器,析构指定迭代器范围内元素
    _Destroy(_ForwardIterator __first, _ForwardIterator __last,
	     _Allocator& __alloc)
    { //调用内存分配器_Allocator的destroy函数析构元素
      typedef __gnu_cxx::__alloc_traits<_Allocator> __traits;
      for (; __first != __last; ++__first)
		__traits::destroy(__alloc, std::__addressof(*__first));
    }

  template<typename _ForwardIterator, typename _Tp> //析构函数模板,模板参数为迭代器类型和对象类型
    inline void //内存分配器为std::allocator,析构迭代器范围内元素
    _Destroy(_ForwardIterator __first, _ForwardIterator __last,
	     allocator<_Tp>&)
    {
      _Destroy(__first, __last);
    }
} // namespace std 
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值