六 配接器(三)function adapters

本文深入探讨了C++中仿函数配接器的功能与应用,包括对返回值的否定、参数绑定、函数合成、函数指针转换为仿函数以及成员函数指针的适配。通过具体实例,展示了如何利用这些配接器实现更灵活的代码结构与功能扩展。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

一 仿函数配接器种类:

(1)对返回值进行逻辑否定:not1,not2。

(2)对参数进行绑定:bind1st,bind2st。

(3) 用于函数合成:compose1,compose2。

(4)用于函数指针:ptr_fun。

(5)用于成员函数指针:mem_fun、mem_fun_ref。

如下图:


二 对返回值进行否定:

(1)源代码:

1. not1:

 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); }
    };


  //辅助函数
  template <class _Predicate>
    inline unary_negate<_Predicate>
    not1(const _Predicate& __pred)
    { return unary_negate<_Predicate>(__pred); }


2. not2:

 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); }
    };

//辅助函数
  template <class _Predicate>
    inline binary_negate<_Predicate>
    not2(const _Predicate& __pred)
    { return binary_negate<_Predicate>(__pred); }


(2)使用方法:

struct display
{
void operator()(const int &data)
{
if(not2(less<int>())(data,4))//使用辅助函数
//if(binary_negate<less<int> >(less<int>())(data,4))//直接使用类。
cout<<data<<endl;
}
};
int main()
{
int array[]={1,2,3,4,5,6};
vector<int> vec(array,array+6);
for_each(vec.begin(),vec.end(),display());//输出456.
}


三 对参数进行绑定:bind1st、bind2nd。(STL不支持三元仿函数)

(1)源代码:

1.bind1nd

  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); }


      // _GLIBCXX_RESOLVE_LIB_DEFECTS
      // 109.  Missing binders for non-const sequence elements
      typename _Operation::result_type
      operator()(typename _Operation::second_argument_type& __x) const
      { return op(value, __x); }
    };


  //辅助函数
  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));
    }

(2)bind2nd:

  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); }


      // _GLIBCXX_RESOLVE_LIB_DEFECTS
      // 109.  Missing binders for non-const sequence elements
      typename _Operation::result_type
      operator()(typename _Operation::first_argument_type& __x) const
      { return op(__x, value); }
    };


  //辅助函数
  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));
    }


(2)使用方法:

struct display
{
void operator()(const int &data)
{
if(bind2nd(less<int>(),4)(data))
cout<<data<<endl;
}
};
int main()
{
int array[]={1,2,3,4,5,6};
vector<int> vec(array,array+6);
for_each(vec.begin(),vec.end(),display());//输出123.
}


四 用于函数合成:compose1和compose2(未纳入STL标准)

(1)源代码:


五 用于函数指针:ptr_fun

这种配接器允许我们将一般函数当做仿函数使用。一般函数无配接能力,所以需要使用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() {}


      explicit
      pointer_to_unary_function(_Result (*__x)(_Arg))
      : _M_ptr(__x) {}


      _Result
      operator()(_Arg __x) const
      { return _M_ptr(__x); }
    };


  //辅助函数
  template <class _Arg, class _Result>
    inline pointer_to_unary_function<_Arg, _Result>
    ptr_fun(_Result (*__x)(_Arg))
    { return pointer_to_unary_function<_Arg, _Result>(__x); }


  /// One of the @link s20_3_7_adaptors adaptors for function pointers@endlink.
  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() {}


      explicit
      pointer_to_binary_function(_Result (*__x)(_Arg1, _Arg2))
      : _M_ptr(__x) {}


      _Result
      operator()(_Arg1 __x, _Arg2 __y) const
      { return _M_ptr(__x, __y); }
    };


  /// One of the @link s20_3_7_adaptors adaptors for function pointers@endlink.
  template <class _Arg1, class _Arg2, class _Result>
    inline pointer_to_binary_function<_Arg1, _Arg2, _Result>//辅助函数
    ptr_fun(_Result (*__x)(_Arg1, _Arg2))
    { return pointer_to_binary_function<_Arg1, _Arg2, _Result>(__x); }
  /** @}  */


六 用于成员函数指针:men_fun和men_fun_ref.

(1)源代码如下:

*  There are a total of 16 = 2^4 function objects in this family.
   *   (1) Member functions taking no arguments vs member functions taking
   *        one argument.
   *   (2) Call through pointer vs call through reference.
   *   (3) Member function with void return type vs member function with
   *       non-void return type.
   *   (4) Const vs non-const member function.
   *
   *  Note that choice (3) is nothing more than a workaround: according
   *   to the draft, compilers should handle void and non-void the same way.
   *   This feature is not yet widely implemented, though.  You can only use
   *   member functions returning void if your compiler supports partial
   *   specialization.
   *
   *  All of this complexity is in the function objects themselves.  You can
   *   ignore it by using the helper function mem_fun and mem_fun_ref,
   *   which create whichever type of adaptor is appropriate.
   *
   *  @{
   */
  /// One of the @link s20_3_8_memadaptors adaptors for member pointers@endlink.
  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)();
    };


  /// One of the @link s20_3_8_memadaptors adaptors for member pointers@endlink.
  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;
    };


  /// One of the @link s20_3_8_memadaptors adaptors for member pointers@endlink.
  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)();
  };


  /// One of the @link s20_3_8_memadaptors adaptors for member pointers@endlink.
  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;
    };


  /// One of the @link s20_3_8_memadaptors adaptors for member pointers@endlink.
  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);
    };


  /// One of the @link s20_3_8_memadaptors adaptors for member pointers@endlink.
  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;
    };


  /// One of the @link s20_3_8_memadaptors adaptors for member pointers@endlink.
  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);
    };


  /// One of the @link s20_3_8_memadaptors adaptors for member pointers@endlink.
  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;
    };


  /// One of the @link s20_3_8_memadaptors adaptors for member pointers@endlink.
  template <class _Tp>
    class mem_fun_t<void, _Tp> : public unary_function<_Tp*, void>
    {
    public:
      explicit
      mem_fun_t(void (_Tp::*__pf)())
      : _M_f(__pf) {}


      void
      operator()(_Tp* __p) const
      { (__p->*_M_f)(); }
    private:
      void (_Tp::*_M_f)();
    };


  /// One of the @link s20_3_8_memadaptors adaptors for member pointers@endlink.
  template <class _Tp>
    class const_mem_fun_t<void, _Tp> : public unary_function<const _Tp*, void>
    {
    public:
      explicit
      const_mem_fun_t(void (_Tp::*__pf)() const)
      : _M_f(__pf) {}


      void
      operator()(const _Tp* __p) const
      { (__p->*_M_f)(); }
    private:
      void (_Tp::*_M_f)() const;
    };


  /// One of the @link s20_3_8_memadaptors adaptors for member pointers@endlink.
  template <class _Tp>
    class mem_fun_ref_t<void, _Tp> : public unary_function<_Tp, void>
    {
    public:
      explicit
      mem_fun_ref_t(void (_Tp::*__pf)())
      : _M_f(__pf) {}


      void
      operator()(_Tp& __r) const
      { (__r.*_M_f)(); }
    private:
      void (_Tp::*_M_f)();
    };


  /// One of the @link s20_3_8_memadaptors adaptors for member pointers@endlink.
  template <class _Tp>
    class const_mem_fun_ref_t<void, _Tp> : public unary_function<_Tp, void>
    {
    public:
      explicit
      const_mem_fun_ref_t(void (_Tp::*__pf)() const)
      : _M_f(__pf) {}


      void
      operator()(const _Tp& __r) const
      { (__r.*_M_f)(); }
    private:
      void (_Tp::*_M_f)() const;
    };


  /// One of the @link s20_3_8_memadaptors adaptors for member pointers@endlink.
  template <class _Tp, class _Arg>
    class mem_fun1_t<void, _Tp, _Arg> : public binary_function<_Tp*, _Arg, void>
    {
    public:
      explicit
      mem_fun1_t(void (_Tp::*__pf)(_Arg))
      : _M_f(__pf) {}


      void
      operator()(_Tp* __p, _Arg __x) const
      { (__p->*_M_f)(__x); }
    private:
      void (_Tp::*_M_f)(_Arg);
    };


  /// One of the @link s20_3_8_memadaptors adaptors for member pointers@endlink.
  template <class _Tp, class _Arg>
    class const_mem_fun1_t<void, _Tp, _Arg>
    : public binary_function<const _Tp*, _Arg, void>
    {
    public:
      explicit
      const_mem_fun1_t(void (_Tp::*__pf)(_Arg) const)
      : _M_f(__pf) {}


      void
      operator()(const _Tp* __p, _Arg __x) const
      { (__p->*_M_f)(__x); }
    private:
      void (_Tp::*_M_f)(_Arg) const;
    };


  /// One of the @link s20_3_8_memadaptors adaptors for member pointers@endlink.
  template <class _Tp, class _Arg>
    class mem_fun1_ref_t<void, _Tp, _Arg>
    : public binary_function<_Tp, _Arg, void>
    {
    public:
      explicit
      mem_fun1_ref_t(void (_Tp::*__pf)(_Arg))
      : _M_f(__pf) {}


      void
      operator()(_Tp& __r, _Arg __x) const
      { (__r.*_M_f)(__x); }
    private:
      void (_Tp::*_M_f)(_Arg);
    };


  /// One of the @link s20_3_8_memadaptors adaptors for member pointers@endlink.
  template <class _Tp, class _Arg>
    class const_mem_fun1_ref_t<void, _Tp, _Arg>
    : public binary_function<_Tp, _Arg, void>
    {
    public:
      explicit
      const_mem_fun1_ref_t(void (_Tp::*__pf)(_Arg) const)
      : _M_f(__pf) {}


      void
      operator()(const _Tp& __r, _Arg __x) const
      { (__r.*_M_f)(__x); }
    private:
      void (_Tp::*_M_f)(_Arg) const;
    };


  // Mem_fun adaptor helper functions.  There are only two:
  // mem_fun and mem_fun_ref.
  template <class _Ret, class _Tp>
    inline mem_fun_t<_Ret, _Tp>
    mem_fun(_Ret (_Tp::*__f)())
    { return mem_fun_t<_Ret, _Tp>(__f); }


  template <class _Ret, class _Tp>
    inline const_mem_fun_t<_Ret, _Tp>
    mem_fun(_Ret (_Tp::*__f)() const)
    { return const_mem_fun_t<_Ret, _Tp>(__f); }


  template <class _Ret, class _Tp>
    inline mem_fun_ref_t<_Ret, _Tp>
    mem_fun_ref(_Ret (_Tp::*__f)())
    { return mem_fun_ref_t<_Ret, _Tp>(__f); }


  template <class _Ret, class _Tp>
    inline const_mem_fun_ref_t<_Ret, _Tp>
    mem_fun_ref(_Ret (_Tp::*__f)() const)
    { return const_mem_fun_ref_t<_Ret, _Tp>(__f); }


  template <class _Ret, class _Tp, class _Arg>
    inline mem_fun1_t<_Ret, _Tp, _Arg>
    mem_fun(_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_fun(_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_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); }









评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值