STL学习_配接器篇

STL学习_配接器篇

  • 定义

    配接器(Adapter)在STL组件的灵活组合运用功能上,扮演着轴承、转换器的角色。它事实上是一种设计模式。即将一个class的接口转换为另一个class的接口,使原本因接口不兼容而不能合作的classes,可以一起运作

  • 分类

    STL所提供的各种适配器中,改变仿函数(functors)接口者,称为function adapter;改变容器(containers)接口者,称为container adapter;改变迭代器(iterators)接口者,称为iterator adapter。

    functor adapters

    functor adapters是所有配接器中数量最庞大的一个族群,其配接灵活度是后两者不能及的,可以配接、配接、在配接。其中配接操作包括系结(bind)、否定(negate)、组合(compose)、以及对一般函数或成员函数的修饰(使其成为一个仿函数)。它的价值在于,通过它们之间的绑定、组合、修饰能力,几乎可以无限制地创造出各种可能的表达式(expression),搭配STL算法一起演出。

    由于仿函数就是“将function call操作符重载”的一种class,而任何算法接受一个仿函数时,总是在其演算过程中调用该仿函数的operator(),这使得不具备仿函数之形、却有真函数之实的“一般函数”和“成员函数(member functions)感到为难。如果”一般函数“和“成员函数”不能纳入复用的体系中,则STL的规划将崩落了一角。为此,STL提供了为数众多的配接器,使“一般函数”和“成员函数”得以无缝地与其他配接器或算法结合起来。

    注意,所有期望获取配接能力的组件,本身都必须是可配接的,即一元仿函数必须继承自unary_function,二元仿函数必须继承自binary_function,成员函数必须以mem_fun处理过,一般函数必须以ptr_fun处理过。一个未经ptr_fun处理过的一般函数,虽然也可以函数指针的形式传给STL算法使用,却无法拥有任何配接能力

    container adapters

    STL提供了两个容器queue和stack,其实都只不过是一种配接器。它们修饰deque的接口而成就出另一种风貌。queue和stack底层都是由deque构成的,它们封住所有deque对外接口,只开发符合对应原则的几个函数,故它们是适配器,是一个作用于容器之上的适配器。

    iterator adapters

    STL提供了许多应用于迭代器身上的配接器,包括insert iterators,reverse iterators,iostream iterators。insert iterators可以将一般迭代器的赋值(assign)操作转变为插入(insert)操作。此迭代器包括专门从尾端插入操作back_insert_iterator,专门从头端插入操作front_insert_iterator,以及可从任何位置执行插入操作的insert_iterator。因iterator adapters使用接口不是十分直观,STL提供三个相应的函数back_inserter()、front_inserter()、inserter(),从而提高使用时的便利性。reverse iterators可以将一般迭代器的行进方向逆转,使原本应该前进的operator++变成了后退操作,使原本应该后退的operator–变成了前进操作。此操作用在“从尾端开始进行”的算法上,有很大的方便性。iostream\ iterators可以将迭代器绑定到某个iostream对象身上。绑定到istream对象身上,为istream_iterator,拥有输入功能;绑定到ostream对象身上,成为ostream_iterator,拥有输出功能。此迭代器用在屏幕输出上,非常方便。

  • 源码分析

    1)insert iterator

    // iterator adapter迭代器配接器,用来将某个迭代器的赋值(assign)操作
    // 修改为插入(insert)操作——从容器的尾端插入进去,故称为back_insert
    template <class _Container>
    class back_insert_iterator {
    protected:
      _Container* container;     // 底部容器
    public:
      typedef _Container          container_type;      // 注意类型
      typedef output_iterator_tag iterator_category;
      typedef void                value_type;
      typedef void                difference_type;
      typedef void                pointer;
      typedef void                reference;
      // 使用back_insert_iterator与容器绑定起来
      explicit back_insert_iterator(_Container& __x) : container(&__x) {}
      back_insert_iterator<_Container>&
      operator=(const typename _Container::value_type& __value) { 
        container->push_back(__value);    // 关键,转而调用push_back()
        return *this;
      }
      // 以下三个操作符对back_insert_iterator不起作用(关闭功能)
      // 三个操作符返回的都是back_insert_iterator自己
      back_insert_iterator<_Container>& operator*() { return *this; }
      back_insert_iterator<_Container>& operator++() { return *this; }
      back_insert_iterator<_Container>& operator++(int) { return *this; }
    };
    // 辅助函数,便于使用back_insert_iterator 
    template <class _Container>
    inline back_insert_iterator<_Container> back_inserter(_Container& __x) {
      return back_insert_iterator<_Container>(__x);
    
    // 这是一个迭代器配接器(iterator adapter),用来将某个迭代器的赋值(assign)操作修改为插入(insert)
    // 操作——从容器的头端插入进去(称为front_insert)
    // 注意,该迭代器不适用于vector,因为vector都没提供push_front函数
    template <class _Container>
    class front_insert_iterator {
    protected:
      _Container* container;   // 底层容器
    public:
      typedef _Container          container_type;       // 注意类型
      typedef output_iterator_tag iterator_category;
      typedef void                value_type;
      typedef void                difference_type;
      typedef void                pointer;
      typedef void                reference;
    
      explicit front_insert_iterator(_Container& __x) : container(&__x) {}
      front_insert_iterator<_Container>&
      operator=(const typename _Container::value_type& __value) { 
        container->push_front(__value);    // 此处为关键,转而调用push_front()
        return *this;
      }
      // 以下三个操作符对front_insert_iterator不起作用(关闭功能)
      // 三个操作符返回的都是front_insert_iterator自己
      front_insert_iterator<_Container>& operator*() { return *this; }
      front_insert_iterator<_Container>& operator++() { return *this; }
      front_insert_iterator<_Container>& operator++(int) { return *this; }
    };
    // 辅助函数,便于使用front_insert_iterator
    template <class _Container>
    inline front_insert_iterator<_Container> front_inserter(_Container& __x) {
      return front_insert_iterator<_Container>(__x);
    }
    
    // 这是一个迭代器适配器(iterator adapter),用来将某个迭代器的赋值assign操作修改为插入(insert)
    // 操作,在指定的位置上进行,并将迭代器右移一个位置——如此便可很方便地连续执行“表面上是赋值(覆写)
    // 而实际上是插入”的操作。
    template <class _Container>
    class insert_iterator {
    protected:
      _Container* container;     // 底层容器
      typename _Container::iterator iter;
    public:
      typedef _Container          container_type;      // 注意类型
      typedef output_iterator_tag iterator_category;
      typedef void                value_type;
      typedef void                difference_type;
      typedef void                pointer;
      typedef void                reference;
    
      insert_iterator(_Container& __x, typename _Container::iterator __i) 
        : container(&__x), iter(__i) {}
      insert_iterator<_Container>&
      operator=(const typename _Container::value_type& __value) { 
        iter = container->insert(iter, __value);   // 此处为关键,转调用insert()函数
        ++iter;      // 注意此处,使insert_iterator永远随其目标贴身移动
        return *this;
      }
      // 以下三个操作符对insert_iterator不起作用(关闭功能)
      // 三个操作符返回的都是insert_iterator自己
      insert_iterator<_Container>& operator*() { return *this; }
      insert_iterator<_Container>& operator++() { return *this; }
      insert_iterator<_Container>& operator++(int) { return *this; }
    };
    // 辅助函数,便于使用insert_iterator
    template <class _Container, class _Iterator>
    inline 
    insert_iterator<_Container> inserter(_Container& __x, _Iterator __i)
    {
      typedef typename _Container::iterator __iter;
      return insert_iterator<_Container>(__x, __iter(__i));
    }
    

    2)reverse iterator

    // 迭代器配接器(iterator adapter),用来将某个迭代器逆反前进方向,使前进为后退,后退为前进
    class reverse_iterator {
      typedef reverse_iterator<_RandomAccessIterator, _Tp, _Reference, _Distance>
            _Self;     // 代表逆向迭代器  
    protected:
      _RandomAccessIterator current;    // 记录对应之正向迭代器
    public:
      // 逆向迭代器的5种相应型别(associated types)都和其对应的正向迭代器相同
      typedef random_access_iterator_tag iterator_category;
      typedef _Tp                        value_type;
      typedef _Distance                  difference_type;
      typedef _Tp*                       pointer;
      typedef _Reference                 reference;
    
      reverse_iterator() {}
      // 将reverse_iterator与某个迭代器x系结起来
      explicit reverse_iterator(_RandomAccessIterator __x) : current(__x) {}
      _RandomAccessIterator base() const { return current; }   // 取出对应的正向迭代器
      _Reference operator*() const { return *(current - 1); }
    #ifndef __SGI_STL_NO_ARROW_OPERATOR
      pointer operator->() const { return &(operator*()); }
    #endif /* __SGI_STL_NO_ARROW_OPERATOR */
      // 前进(++)变成后退(--)
      _Self& operator++() {
        --current;
        return *this;
      }
      _Self operator++(int) {
        _Self __tmp = *this;
        --current;
        return __tmp;
      }
      // 后退(--)变成前进(++)
      _Self& operator--() {
        ++current;
        return *this;
      }
      _Self operator--(int) {
        _Self __tmp = *this;
        ++current;
        return __tmp;
      }
      // 前进与后退完全逆转
      _Self operator+(_Distance __n) const {
        return _Self(current - __n);
      }
      _Self& operator+=(_Distance __n) {
        current -= __n;
        return *this;
      }
      _Self operator-(_Distance __n) const {
        return _Self(current + __n);
      }
      _Self& operator-=(_Distance __n) {
        current += __n;
        return *this;
      }
      // 注意:下面第一个*和唯一一个+都会调用本类的operator*和operator+
      // 第二个*则不会(判断法则:完全看处理的型别而定)
      _Reference operator[](_Distance __n) const { return *(*this + __n); }
    };
    

    3)stream iterators

    // input iterator,能够为“来自某一basic_istream”的对象执行格式化输入操作
    template <class _Tp, class _Dist>
    class istream_iterator {
    #ifdef __STL_TEMPLATE_FRIENDS
      template <class _T1, class _D1>
      friend bool operator==(const istream_iterator<_T1, _D1>&,
                             const istream_iterator<_T1, _D1>&);
    #else /* __STL_TEMPLATE_FRIENDS */
      friend bool __STD_QUALIFIER
      operator== __STL_NULL_TMPL_ARGS (const istream_iterator&,
                                       const istream_iterator&);
    #endif /* __STL_TEMPLATE_FRIENDS */
    
    protected:
      istream* _M_stream;
      _Tp _M_value;
      bool _M_end_marker;
      void _M_read() {
        _M_end_marker = (*_M_stream) ? true : false;
        if (_M_end_marker) *_M_stream >> _M_value;      // 关键
        // 以上,输入之后,stream的状态可变,所以下面再判断一次以决定end_marker
        // 当读到eof或读到型别不符的资料,stream即处于false状态
        _M_end_marker = (*_M_stream) ? true : false;
      }
    public:
      typedef input_iterator_tag  iterator_category;
      typedef _Tp                 value_type;
      typedef _Dist               difference_type;
      typedef const _Tp*          pointer;
      typedef const _Tp&          reference;
      // 以上,因身为input iterator,所以采用const比较保险
      istream_iterator() : _M_stream(&cin), _M_end_marker(false) {}
      istream_iterator(istream& __s) : _M_stream(&__s) { _M_read(); }
      reference operator*() const { return _M_value; }
    #ifndef __SGI_STL_NO_ARROW_OPERATOR
      pointer operator->() const { return &(operator*()); }
    #endif /* __SGI_STL_NO_ARROW_OPERATOR */
      // 迭代器前进一个位置,就代表要读取一批数据
      istream_iterator<_Tp, _Dist>& operator++() { 
        _M_read(); 
        return *this;
      }
      istream_iterator<_Tp, _Dist> operator++(int)  {
        istream_iterator<_Tp, _Dist> __tmp = *this;
        _M_read();
        return __tmp;
      }
    };
    
    // output iterator,能够将对象格式化输出到某个basic_ostream上
    template <class _Tp>
    class ostream_iterator {
    protected:
      ostream* _M_stream;       
      const char* _M_string;   // 每次输出后的间隔符号,变量名称为string
    public:
      typedef output_iterator_tag iterator_category;
      typedef void                value_type;
      typedef void                difference_type;
      typedef void                pointer;
      typedef void                reference;
    
      ostream_iterator(ostream& __s) : _M_stream(&__s), _M_string(0) {}
      ostream_iterator(ostream& __s, const char* __c) 
        : _M_stream(&__s), _M_string(__c)  {}
      // 对迭代器做赋值(assign)操作,就代表要输出一批数据
      ostream_iterator<_Tp>& operator=(const _Tp& __value) { 
        *_M_stream << __value;                   // 关键:输出数值
        if (_M_string) *_M_stream << _M_string;  // 如果间隔符号不为空,输出间隔符号
        return *this;
      }
      // 注意以下三个操作
      ostream_iterator<_Tp>& operator*() { return *this; }
      ostream_iterator<_Tp>& operator++() { return *this; } 
      ostream_iterator<_Tp>& operator++(int) { return *this; } 
    };
    

    4)function adapters

    • 对返回值进行逻辑否定:not1,not2

      // 以下配接器用来表示某个Adaptable Predicate的逻辑负值
      template <class _Predicate>
      class unary_negate
        : public unary_function<typename _Predicate::argument_type, bool> {
      protected:
        _Predicate _M_pred;      // 内部成员
      public:
        explicit unary_negate(const _Predicate& __x) : _M_pred(__x) {}
        bool operator()(const typename _Predicate::argument_type& __x) const {
          return !_M_pred(__x);  // 将pred的运算结果加上否定(negate)运算
        }
      };
      // 辅助函数,以便于使用unary_negate<_Predicate> 
      template <class _Predicate>
      inline unary_negate<_Predicate> 
      not1(const _Predicate& __pred)
      {
        return unary_negate<_Predicate>(__pred);
      }
      // 以下适配器用来表示某个Adapter Binary Predicate的逻辑负值
      template <class _Predicate> 
      class binary_negate 
        : public binary_function<typename _Predicate::first_argument_type,
                                 typename _Predicate::second_argument_type,
                                 bool> {
      protected:
        _Predicate _M_pred;             // 内部成员
      public:
        explicit binary_negate(const _Predicate& __x) : _M_pred(__x) {}
        bool operator()(const typename _Predicate::first_argument_type& __x, 
                        const typename _Predicate::second_argument_type& __y) const
        {
          return !_M_pred(__x, __y);    // 将pred的运算结果加上否定(negate)运算 
        }
      };
      // 辅助函数,便于使用binary_negate<_Predicate>
      template <class _Predicate>
      inline binary_negate<_Predicate> 
      not2(const _Predicate& __pred)
      {
        return binary_negate<_Predicate>(__pred);
      }
      
    • 对参数进行绑定:bind1st,bind2nd

      // 以下配接器用来将某个Adapter Binary function转换为Unary Function
      template <class _Operation> 
      class binder1st
        : public unary_function<typename _Operation::second_argument_type,
                                typename _Operation::result_type> {
      protected:
        _Operation op;    // 内部成员
        typename _Operation::first_argument_type value;  // 内部成员
      public:
        binder1st(const _Operation& __x,
                  const typename _Operation::first_argument_type& __y)
            : op(__x), value(__y) {}    // 将表达式和第一参数记录于内部成员
        typename _Operation::result_type
        operator()(const typename _Operation::second_argument_type& __x) const {
          return op(value, __x);        // 实际调用表达式,并将value绑定为第一参数
        }
      };
      // 辅助函数,方便应用binder1st<_Operation>
      template <class _Operation, class _Tp>
      inline binder1st<_Operation> 
      bind1st(const _Operation& __fn, const _Tp& __x) 
      {
        typedef typename _Operation::first_argument_type _Arg1_type;
        return binder1st<_Operation>(__fn, _Arg1_type(__x));
      }
      // 以下配接器用来将Adaptable Binary function转换为Unary Function
      template <class _Operation> 
      class binder2nd
        : public unary_function<typename _Operation::first_argument_type,
                                typename _Operation::result_type> {
      protected:
        _Operation op;     // 内部成员
        typename _Operation::second_argument_type value;    // 内部成员
      public:
        binder2nd(const _Operation& __x,
                  const typename _Operation::second_argument_type& __y) 
            : op(__x), value(__y) {}   // 将表达式和第一参数记录于内部成员
        typename _Operation::result_type
        operator()(const typename _Operation::first_argument_type& __x) const {
          return op(__x, value);       // 实际调用表达式,并将value绑定为第二参数
        }
      };
      // 辅助函数,便于使用binder2nd<_Operation>
      template <class _Operation, class _Tp>
      inline binder2nd<_Operation> 
      bind2nd(const _Operation& __fn, const _Tp& __x) 
      {
        typedef typename _Operation::second_argument_type _Arg2_type;
        return binder2nd<_Operation>(__fn, _Arg2_type(__x));
      }
      
    • 用于函数合成:compose1,compose2

      // 已知两个Adapter Unary Functions f(),g(),以下配接器用来产生一个h(),使得h(x) = f(g(x))
      template <class _Operation1, class _Operation2>
      class unary_compose
        : public unary_function<typename _Operation2::argument_type,
                                typename _Operation1::result_type> 
      {
      protected:
        _Operation1 _M_fn1;   // 内部成员
        _Operation2 _M_fn2;   // 内部成员
      public:
        unary_compose(const _Operation1& __x, const _Operation2& __y) 
          : _M_fn1(__x), _M_fn2(__y) {}    // 将两个表达式记录于内部成员
        typename _Operation1::result_type
        operator()(const typename _Operation2::argument_type& __x) const {
          return _M_fn1(_M_fn2(__x));      // 函数合成
        }
      };
      // 辅助函数,让我们得以方便运用unary_compose<_Operation1,_Operation2>
      template <class _Operation1, class _Operation2>
      inline unary_compose<_Operation1,_Operation2> 
      compose1(const _Operation1& __fn1, const _Operation2& __fn2)
      {
        return unary_compose<_Operation1,_Operation2>(__fn1, __fn2);
      }
      // 已知一个Adapter Binary Function f和两个Adaptable Unary Functions g1,g2
      // 以下配接器用来产生一个h,使h(x) = f(g1(x), g2(x))
      template <class _Operation1, class _Operation2, class _Operation3>
      class binary_compose
        : public unary_function<typename _Operation2::argument_type,
                                typename _Operation1::result_type> {
      protected:
        _Operation1 _M_fn1;     // 内部成员
        _Operation2 _M_fn2;     // 内部成员
        _Operation3 _M_fn3;     // 内部成员
      public:
        binary_compose(const _Operation1& __x, const _Operation2& __y, 
                       const _Operation3& __z) 
          : _M_fn1(__x), _M_fn2(__y), _M_fn3(__z) { }
        typename _Operation1::result_type
        operator()(const typename _Operation2::argument_type& __x) const {
          return _M_fn1(_M_fn2(__x), _M_fn3(__x));   // 函数合成
        }
      };
      // 辅助函数,让我们得以方便运用binary_compose<_Operation1,_Operation2,_Operation3>
      template <class _Operation1, class _Operation2, class _Operation3>
      inline binary_compose<_Operation1, _Operation2, _Operation3> 
      compose2(const _Operation1& __fn1, const _Operation2& __fn2, 
               const _Operation3& __fn3)
      {
        return binary_compose<_Operation1,_Operation2,_Operation3>
          (__fn1, __fn2, __fn3);
      }
      
    • 用于函数指针:ptr_fun

      // 以下配接器其实就是把一个一元函数指针包起来;
      // 当仿函数被使用时,就调用该函数指针
      template <class _Arg, class _Result>
      class pointer_to_unary_function : public unary_function<_Arg, _Result> {
      protected:
        _Result (*_M_ptr)(_Arg);     // 内部成员,一个函数指针
      public:
        pointer_to_unary_function() {}
        // 以下constructor将函数指针记录于内部成员之中
        explicit pointer_to_unary_function(_Result (*__x)(_Arg)) : _M_ptr(__x) {}
        // 通过函数指针执行函数
        _Result operator()(_Arg __x) const { return _M_ptr(__x); }
      };
      // 辅助函数,使我们能够方便运用pointer_to_unary_function
      template <class _Arg, class _Result>
      // pointer_to_unary_function<_Arg, _Result>是函数的返回值
      inline pointer_to_unary_function<_Arg, _Result> ptr_fun(_Result (*__x)(_Arg))
      {
        return pointer_to_unary_function<_Arg, _Result>(__x);
      }
      // 以下配接器其实就是把一个二元函数指针包起来;
      // 当仿函数被使用时,就调用该函数指针
      template <class _Arg1, class _Arg2, class _Result>
      class pointer_to_binary_function : 
        public binary_function<_Arg1,_Arg2,_Result> {
      protected:
          _Result (*_M_ptr)(_Arg1, _Arg2);   // 内部成员,一个函数指针
      public:
          pointer_to_binary_function() {}
          // 以下constructor将函数指针记录于内部成员之中
          explicit pointer_to_binary_function(_Result (*__x)(_Arg1, _Arg2)) 
            : _M_ptr(__x) {}
          // 以下,通过函数指针执行函数
          _Result operator()(_Arg1 __x, _Arg2 __y) const {
            return _M_ptr(__x, __y);
          }
      };
      // 辅助函数,使我们能够方便运用pointer_to_binary_function
      template <class _Arg1, class _Arg2, class _Result>
      // pointer_to_binary_function<_Arg1,_Arg2,_Result>是函数的返回值
      inline pointer_to_binary_function<_Arg1,_Arg2,_Result> 
      ptr_fun(_Result (*__x)(_Arg1, _Arg2)) {
        return pointer_to_binary_function<_Arg1,_Arg2,_Result>(__x);
      }
      
    • 用于成员函数指针:mem_fun,men_fun_ref

      // 这个族群一共有8 = 2^3个function objects
      // 1)“无任何参数”vs“有一个参数”
      // 2)“通过pointer调用”vs“通过refernece调用”
      // 3)“const成员函数”vs“non-const成员函数”
      // 所有复杂都只存在于function objects内部。可以忽略它们,直接使用更上层的辅助函数mem_fun和
      // mem_fun_ref,它们会产生适当的配接器
      // “无任何参数”、“通过pointer调用”、“non-const成员函数”
      template <class _Ret, class _Tp>
      class mem_fun_t : public unary_function<_Tp*,_Ret> {
      public:
        explicit mem_fun_t(_Ret (_Tp::*__pf)()) : _M_f(__pf) {}    // 记录下来
        _Ret operator()(_Tp* __p) const { return (__p->*_M_f)(); } // 转调用
      private:
        _Ret (_Tp::*_M_f)();  // 内部成员,pointer to member function
      };
      // “无任何参数”、“通过pointer调用”、“const成员函数”
      template <class _Ret, class _Tp>
      class const_mem_fun_t : public unary_function<const _Tp*,_Ret> {
      public:
        explicit const_mem_fun_t(_Ret (_Tp::*__pf)() const) : _M_f(__pf) {}
        _Ret operator()(const _Tp* __p) const { return (__p->*_M_f)(); }
      private:
        _Ret (_Tp::*_M_f)() const;   // 内部成员,pointer to const member function 
      };
      
      // “无任何参数”、“通过reference调用”、“non-const成员函数”
      template <class _Ret, class _Tp>
      class mem_fun_ref_t : public unary_function<_Tp,_Ret> {
      public:
        explicit mem_fun_ref_t(_Ret (_Tp::*__pf)()) : _M_f(__pf) {}  // 记录下来
        _Ret operator()(_Tp& __r) const { return (__r.*_M_f)(); }    // 转调用
      private:
        _Ret (_Tp::*_M_f)();   // 内部成员,pointer to member function
      };
      // “无任何参数”、“通过reference调用”、“const成员函数”
      template <class _Ret, class _Tp>
      class const_mem_fun_ref_t : public unary_function<_Tp,_Ret> {
      public:
        explicit const_mem_fun_ref_t(_Ret (_Tp::*__pf)() const) : _M_f(__pf) {}
        _Ret operator()(const _Tp& __r) const { return (__r.*_M_f)(); }
      private:
        _Ret (_Tp::*_M_f)() const;   // 内部成员,pointer to const member function 
      };
      // “有一个参数”、“通过pointer调用”、“non-const成员函数”
      template <class _Ret, class _Tp, class _Arg>
      class mem_fun1_t : public binary_function<_Tp*,_Arg,_Ret> {
      public:
        explicit mem_fun1_t(_Ret (_Tp::*__pf)(_Arg)) : _M_f(__pf) {}              // 转录下来
        _Ret operator()(_Tp* __p, _Arg __x) const { return (__p->*_M_f)(__x); }   // 转调用
      private:
        _Ret (_Tp::*_M_f)(_Arg);    // 内部成员,pointer to member function 
      };
      // “有一个参数”、“通过pointer调用”、“const成员函数”
      template <class _Ret, class _Tp, class _Arg>
      class const_mem_fun1_t : public binary_function<const _Tp*,_Arg,_Ret> {
      public:
        explicit const_mem_fun1_t(_Ret (_Tp::*__pf)(_Arg) const) : _M_f(__pf) {}
        _Ret operator()(const _Tp* __p, _Arg __x) const
          { return (__p->*_M_f)(__x); }
      private:
        _Ret (_Tp::*_M_f)(_Arg) const;   // 内部成员,pointer to const member function
      };
      // “有一个参数”、“通过reference调用”、“non-const成员函数”
      template <class _Ret, class _Tp, class _Arg>
      class mem_fun1_ref_t : public binary_function<_Tp,_Arg,_Ret> {
      public:
        explicit mem_fun1_ref_t(_Ret (_Tp::*__pf)(_Arg)) : _M_f(__pf) {}        // 记录下来
        _Ret operator()(_Tp& __r, _Arg __x) const { return (__r.*_M_f)(__x); }  // 转调用
      private:
        _Ret (_Tp::*_M_f)(_Arg);    // 内部成员,pointer to member function
      };
      // “有一个参数”、“通过reference调用”、“const成员函数”
      template <class _Ret, class _Tp, class _Arg>
      class const_mem_fun1_ref_t : public binary_function<_Tp,_Arg,_Ret> {
      public:
        explicit const_mem_fun1_ref_t(_Ret (_Tp::*__pf)(_Arg) const) : _M_f(__pf) {}
        _Ret operator()(const _Tp& __r, _Arg __x) const { return (__r.*_M_f)(__x); }
      private:
        _Ret (_Tp::*_M_f)(_Arg) const;   // 内部成员,pointer to const member function
      };
      
      // mem_fun adapter的辅助函数:mem_fun,mem_fun_ref
      template <class _Ret, class _Tp, class _Arg>
      inline mem_fun1_ref_t<_Ret,_Tp,_Arg> mem_fun_ref(_Ret (_Tp::*__f)(_Arg))
        { return mem_fun1_ref_t<_Ret,_Tp,_Arg>(__f); }
      
      template <class _Ret, class _Tp, class _Arg>
      inline const_mem_fun1_ref_t<_Ret,_Tp,_Arg>
      mem_fun_ref(_Ret (_Tp::*__f)(_Arg) const)
        { return const_mem_fun1_ref_t<_Ret,_Tp,_Arg>(__f); }
      // 以下四个函数,其实可以采用和先前(以上)四个函数相同的名称(函数重载)
      template <class _Ret, class _Tp, class _Arg>
      inline mem_fun1_t<_Ret,_Tp,_Arg> mem_fun1(_Ret (_Tp::*__f)(_Arg))
        { return mem_fun1_t<_Ret,_Tp,_Arg>(__f); }
      
      template <class _Ret, class _Tp, class _Arg>
      inline const_mem_fun1_t<_Ret,_Tp,_Arg> mem_fun1(_Ret (_Tp::*__f)(_Arg) const)
        { return const_mem_fun1_t<_Ret,_Tp,_Arg>(__f); }
      
      template <class _Ret, class _Tp, class _Arg>
      inline mem_fun1_ref_t<_Ret,_Tp,_Arg> mem_fun1_ref(_Ret (_Tp::*__f)(_Arg))
        { return mem_fun1_ref_t<_Ret,_Tp,_Arg>(__f); }
      
      template <class _Ret, class _Tp, class _Arg>
      inline const_mem_fun1_ref_t<_Ret,_Tp,_Arg>
      mem_fun1_ref(_Ret (_Tp::*__f)(_Arg) const)
        { return const_mem_fun1_ref_t<_Ret,_Tp,_Arg>(__f); }
      
  • 参考文献

    STL源码剖析——侯捷

    STL源码

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值