c++ - 在 C++ 中回调类成员

标签 c++ function methods callback

我们为客户提供了一个简单的通信库。

我的问题是:如何保存指向客户类的方法的指针?

Library.h 是包含客户建立通信所需的所有方法的头文件。

library.cpp 是我们的代码。我必须在这里的某个地方保存指向我们客户的回调函数方法的指针。

customer.cpp 是客户如何使用我们的库的示例。

library.h:

// This is the header file what our customer gets
class Library {
  public:
    template <class Object, class Function>
    void SetCallback(Object &obj, Function f);
};

library.cpp:

struct T_CUSTOMER {
    Object o;   // <- ???
    Function f; // <- ???
} customer;

void Library::SetCallback(Object &obj, Function f) {
    //Saving the method from our costumer
    customer.o = obj;   // <- ???
    customer.f = f;     // <- ???
}

void someFunction(void) {
    // here i want to call the method from the customer
    customer.o->customer.f(); //<- ???
}

customer.cpp:

class AnyCustomerClass {
    private:
        Library lib;

    public:
        AnyCustomerClass() {
            //< here the customer sets his method which I should call
            lib.SetCallback(this, &AnyCustomerClass::callback());
        }

        callback() {
            // do something
        }
}

感谢您的帮助!

最佳答案

基本思想是,你定义一个抽象的回调类,它实际上被传递给你的接口(interface)。这个回调一个传递单个 int 参数的函数:

struct Callback {
  virtual ~Callback(){}
  virtual void operator()(int param)=0;
};

此类允许您的实现无需了解您需要回调的代码。当然,要调用一个类,您确实需要一个知道其目标的 Callback 实例。因此,您还可以提供一个模板化的子类,使您的库的用户可以轻松地将其中一个类中的方法绑定(bind)到通用回调的实例:-

template<class T>
class ClassCallback : public Callback {
  T* _classPtr;
  typedef void(T::*fncb)(int param);
  fncb _cbProc;
public:
  ClassCallback(T* classPtr,fncb cbProc):_classPtr(classPtr),_cbProc(cbProc){}
  virtual void operator()(int param){
    (_classPtr->*_cbProc)(param);
  }
};

要从他们的类创建回调的实例,代码如下所示。调用也很简单:

struct CMyClass {
  Library* _theLibrary;
  CMyClass(Library* init):_theLibrary(init){
    Callback* pCB = new ClassCallback<CMyClass>(&myClass,&CMyClass::OnCb);
    _theLibrary->SetCallback(pCB);
  }
  void OnCb(int){
    // callback triggered
  }
  void Run(){
    _theLibrary->DoWork();
  }
};

总结:Library.h 看起来像这样。定义抽象回调类、您的库类以及客户用来包装其类及其回调方法的模板化实用程序类:

// This is the header file what our customer gets
struct Callback {... };
class Library {
  Callback* _pcb;
  public:
    void SetCallback(Callback* pcb){_pcb=pcb;}
    void DoWork(){
      int status=0;
      (*pcb)(status);
    }
    ~Library(){delete _pcb;}

};
template<class T> struct ClassCallback{ ... };

关于c++ - 在 C++ 中回调类成员,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/4919308/

相关文章:

c++ - 如何使用 linux 命令传递输入和配置文件

C++ 重新声明不一致/有趣

c - 如何使用文件和 malloc 构造函数

java - 方法调用不起作用?(Java NullPointerException)

c++ - MFC Visual Studio 中的代码错误 CString?

c++ - 使用 ffmpeg 获取文件信息,目标文件被识别为音频?

c++ - 如何在http代理后面使用ftp url下载文件

c - 尝试读取文本文件时遇到错误

java - 相同 instanceof 但不同类的方法不可见性

java - java中两个同名的方法