如何键入一个指向方法的指针,该方法返回一个指针方法?

时间:2008-10-02 05:20:06

标签: c++ member-function-pointers

基本上我有以下课程:

class StateMachine {
...
StateMethod stateA();
StateMethod stateB();
...
};

stateA()和stateB()方法应该能够返回指向stateA()和stateB()的指针。 如何输入定义StateMethod?

5 个答案:

答案 0 :(得分:14)

GotW #57表示为此目的使用带隐式转换的代理类。

struct StateMethod;
typedef StateMethod (StateMachine:: *FuncPtr)(); 
struct StateMethod
{
  StateMethod( FuncPtr pp ) : p( pp ) { }
  operator FuncPtr() { return p; }
  FuncPtr p;
};

class StateMachine {
  StateMethod stateA();
  StateMethod stateB();
};

int main()
{
  StateMachine *fsm = new StateMachine();
  FuncPtr a = fsm->stateA();  // natural usage syntax
  return 0;
}    

StateMethod StateMachine::stateA
{
  return stateA; // natural return syntax
}

StateMethod StateMachine::stateB
{
  return stateB;
}
  

这个解决方案主要有三个   优势:

     
      
  1. 它可以根据需要解决问题。更好的是,它是类型安全的   便携式的。

  2.   
  3. 它的机制是透明的:你得到了自然的语法   调用者/用户,以及自然语法   函数自己的“返回状态A”;   言。

  4.   
  5. 它的开销可能为零:在现代编译器中,代理类,   应有的存储和功能   内联并优化至零。

  6.   

答案 1 :(得分:8)

只使用typedef:

class StateMachine {  

 public:  

  class StateMethod;     
  typedef StateMethod (StateMachine::*statemethod)();   

  class StateMethod {  

    statemethod   method; 
    StateMachine& obj; 

   public:  

    StateMethod(statemethod method_, StateMachine *obj_)  
      : method(method_), obj(*obj_) {} 

    StateMethod operator()() { return (obj.*(method))(); }  
  };  

  StateMethod stateA()  { return StateMethod(&StateMachine::stateA, this); }  

  StateMethod stateB()  { return StateMethod(&StateMachine::stateB, this); }  

};    

答案 2 :(得分:3)

编辑:njsf在这里证明我错了。但是,您可能会发现静态构建更容易维护,因此我将其余部分保留在此处。

没有'正确'的静态类型,因为完整类型是递归的:

typedef StateMethod (StateMachine::*StateMethod)();

您最好的选择是使用typedef void (StateMachine::*StateMethod)();,然后执行丑陋的state = (StateMethod)(this->*state)();

PS:boost::function需要明确的返回类型,至少在我阅读docs时需要boost::function0<ReturnType>

答案 3 :(得分:2)

我的理念是不使用原始成员函数指针。我甚至不知道如何使用原始指针typedef做你想做的事情,语法太可怕了。我喜欢使用boost :: function。

几乎肯定错了:

class X
{
  public:
    typedef const boost::function0<Method> Method;

    // some kind of mutually recursive state machine
    Method stateA()
    { return boost::bind(&X::stateB, this); }
    Method stateB()
    { return boost::bind(&X::stateA, this); }
};

这个问题肯定比第一次见到眼睛要难得多

答案 4 :(得分:0)

我永远不会记得可怕的C ++函数declspec,所以每当我必须找出描述成员函数的语法时,我就会产生一个故意的编译器错误,它通常会为我显示正确的语法。

所以给出:

class StateMachine { 
    bool stateA(int someArg); 
};

stateA的typedef的语法是什么?不知道..所以让我们试着给它分配一些不相关的东西,看看编译器说的是什么:

char c = StateMachine::stateA

编译说:

error: a value of type "bool (StateMachine::*)(int)" cannot be used to initialize 
       an entity of type "char" 

它是:“bool(StateMachine :: *)(int)”是我们的typedef。