【问题标题】:How to pass a member function pointer to an overloaded method in a template function?如何将成员函数指针传递给模板函数中的重载方法?
【发布时间】:2011-06-17 04:59:19
【问题描述】:

我提到了这个somewhat similar question。但是这里的情况不同:

struct A
{
  void foo (int i) {} // choice
  void foo (double i) {}
};

template<typename ObjType, typename FuncPtr>
void ReceiveFuncPtr (ObjType o, FuncPtr pf)
{
 (o.*pf)(1);
}

int main ()
{
  A obj;
  ReceiveFuncPtr(obj, &A::foo); // don't want typecast here
}

在上面的测试代码中,我在A 中有一个重载的foo。如果只有 1 个foo,那么代码可以正常工作。但是对于重载的情况,编译器会抱怨:

错误:没有匹配的调用函数 到`ReceiveFuncPtr(A&,[未解决 重载函数类型])'

除了在调用ReceiveFuncPtr() 时进行显式类型转换,我们有什么方法可以对其template 参数进行一些更改,并使其始终能够接收foo(int) 版本,以获取任何类似的class A

编辑:想法是在调用函数时不要担心类型。它应该像ReceiveFuncPtr(obj, &amp;A::foo); 一样简单,然后让template 完成它的工作。

【问题讨论】:

  • 定义“对于任何类似的 A 类”的含义,这样可以更好地帮助您。

标签: c++ templates overloading member-function-pointers


【解决方案1】:

这个怎么样:

template<typename ObjType>
void ReceiveFuncPtr (ObjType o, void (ObjType::*pf)(int))
{
 (o.*pf)(1);
}

【讨论】:

    【解决方案2】:

    函数模板可以写成:

    template<typename ObjType>
    void ReceiveFuncPtr (ObjType o, void (ObjType::*pf)(int) )
    {
       (o.*pf)(1);
    }
    

    这个函数模板会自动选择void foo (int i)


    我之前的回答(不删除,因为可能对其他人有帮助)

    你的问题:

    ReceiveFuncPtr(obj, &A::foo); // don't want typecast here
    

    你可以这样做:

    void (A::*pFun)(int) = &A::foo; // No casting here!
    ReceiveFuncPtr(obj, pFun);      // No casting here!
    

    pFun 是指向void A::f(int) 的指针


    你也可以使用 typedef 为:

    typedef void (A::*FunDouble)(double);
    typedef void (A::*FunInt)(int);
    
    FunInt pFun  = &A::foo;    // No casting here!
    ReceiveFuncPtr(obj, pFun); // No casting here!
    

    【讨论】:

    • 我更喜欢类型转换而不是那个版本:)。想法是在编写代码时不要担心A::foo 类型。模板应该推断它正如我在问题中建议的那样,any way that we can make some changes in its template parameter
    • @iammilind:查看我的最后一个解决方案。 :-)
    • +1,没错。实际上我试过了,但我忘了删除导致错误的第二个模板参数FuncPtr
    • 我建议不要这样做,因为如果您将派生类对象作为第一个参数并将指向基类函数的指针作为第二个参数传递,它会中断。
    猜你喜欢
    • 1970-01-01
    • 2020-10-26
    • 2018-12-07
    • 1970-01-01
    • 2021-11-29
    • 1970-01-01
    • 2016-02-20
    相关资源
    最近更新 更多