2015-07-05 175 views
1

我有一个类Alpha和一个函数pointFun,它应该接受Alpha成员函数和通用外部函数(例如:主定义)。C++接受成员函数指针和外部函数指针

我已覆盖pointFun,使其可通过Alpha成员函数和外部函数使用。但由于pointFun功能其实很长,我想避免重复两遍。

有没有办法接受这两种函数指针类型?我试图做到这一点(请参阅代码的评论部分),但它不起作用。

// fpointer.h 

#include <iostream> 
using std::cout; 
using std::endl; 

class Alpha { 
    public: 
     Alpha() {} 

     void pointFun (void (Alpha::*fun)()); 
     void pointFun (void (*fun)()); 
     //void pointFun (void (*funA)(), void (Alpha::*funB)()); // <-- how to make THIS instead of the previous two? 
     void printA (); 
     void assignF (); 

    private: 
     int value; 
     bool set; 
}; 

void Alpha::pointFun(void (Alpha::*fun)()) { 
    (Alpha().*fun)(); 
} 

void Alpha::pointFun(void (*fun)()) { 
    (*fun)(); 
} 

/* // I want this: 
void Alpha::pointFun(void (*funA)() = 0, void (Alpha::*funB)() = 0) { 
    (*funA)(); 
    (Alpha().*funB)(); 
    // same code, different pointer functions 
} 
*/ 

void Alpha::printA() { 
    cout << "A" << endl; 
    // some long code 
} 

void Alpha::assignF() { 
    pointFun(&Alpha::printA); 
} 

这是主要的:

// MAIN.cpp 

#include <iostream> 
#include "fpointer.h" 
using namespace std; 

void printB() { 
    cout << "B" << endl; 
    // same long code as before 
} 

int main() { 
    Alpha A; 
    A.pointFun(printB); 
    A.assignF(); 
} 
+1

成员ve的实现rsion看起来非常可疑和愚蠢。 –

+0

那么你将如何实现它? (我是新的函数指针) – AndroidGuy

+1

@AndroidGuy应该可以使用正确定义的['std :: function <>'](http://en.cppreference.com/w/cpp/utility/functional/function )模板作为参数。 –

回答

1

您可以创建,这需要std::function的方法,并期待它为你的特殊情况:

class Alpha { 
public: 
    void pointFun (std::function<void()> f); // Long function definition 

    void pointFun (void (Alpha::*fun)()) { pointFun([this, fun](){(this->*fun)();}); } 

// Other stuff 
}; 
+0

那太棒了!但对我来说不起作用:它表示'错误''没有被捕获'。如何解决这个问题? (这是指代码的这一部分:'(this - > * fun)') – AndroidGuy

+1

@AndroidGuy:对不起,忘记捕获'fun'。现在修复。 – Jarod42

+0

谢谢,现在这是完美的:D – AndroidGuy

1

肯定的:

struct Foo 
{ 
    using Fn = R(T1, T2, T3); 

    R execute(Fn * f, T1 a1, T2 a2, T3 a3) 
    //  ^^^^^^ 
    //  free pointer 
    { 
     return f(a1, a2, a3); 
    } 

    R execute(Fn Foo:: *f, T1 a1, T2 a2, T3 a3) 
    //  ^^^^^^^^^^^ 
    //  pointer-to-member 
    { 
     return (this->*f)(a1, a2, a3); 
    } 

    // e.g. 
    R you_can_call_me(T1, T2, T3); 
}; 

R i_am_free(T1, T2, T3); 

R dispatch(bool b, Foo & x, T1 a1, T2 a2, T3 a3) 
{ 
    if (b) { x.execute(&i_am_free, a1, a2, a3); } 
    else { x.execute(&Foo::you_can_call_me, a1, a2, a3); } 
}