简体   繁体   English

我不明白这些功能有何不同

[英]I can't understand how these functions are different

I have callbackType that works if i define the function without a class but when i try to do the same but with a class it just give me an error of conversion. 我有callbackType,如果我在没有类的情况下定义函数,则可以使用,但是当我尝试使用类进行相同的操作时,只会给我带来转换错误。

.h 。H

typedef void(*NclCallback)(NclEvent event, void* userData);
NclCallback callBack;

.cpp .cpp

void callBackF(NclEvent event, void* userData){}

EventManager::EventManager(){
    this->callBack = callBackF; //this works,
    this->callBack = callBackFunction; // this doesn't work
    this->callBack = this->callBackFunction; // this doesn't work
}

void EventManager::callBackFunction(NclEvent event, void* userData){}

The difference is that member functions of a class have an implicit first parameter this which points to the instance of the class that the function was invoked with. 区别在于,类的成员函数具有一个隐式的第一个参数,该参数指向调用该函数的类的实例。 So the difference between your two functions is that the standalone one takes two parameters while the member function takes three parameters. 因此,两个函数之间的区别在于,独立函数具有两个参数,而成员函数具有三个参数。

To solve this problem, you need to use std::bind to bind the callback to the instance of EventManager on which you want it to be called. 要解决此问题,您需要使用std :: bind将回调绑定到您要在其上调用EventManager的实例。 Alternately, you can make the callback function static. 或者,您可以使回调函数为静态。

A function inside a class requires a this pointer that points to the object the function is being called on. 类内部的函数需要this指针, this指针指向正在调用该函数的对象。 Thus, the signature is extended by an extra T* (in your case EventManager* ) that gets passed. 因此,签名通过传递的额外T* (在您的情况下为EventManager* )扩展。 The signatures don't match. 签名不匹配。

You can use static functions to tell the compiler that this function does not operate on a specific instance. 您可以使用static函数来告诉编译器该函数不适用于特定实例。 You won't get a this pointer and your code should work. 您将不会获得this指针,并且您的代码应该可以工作。 If you do need access to an instance pointer, take a look at std::bind . 如果确实需要访问实例指针,请查看std::bind

You can also use std::function and lambdas to store callbacks: 您还可以使用std::function和lambdas存储回调:

std::function<void(int, int)> callback;

void f1(int, int) {
  cout << "one" << endl;
}

struct f2 {
  void operator() (int, int) {
    cout << "two" << endl;
  }
};

struct f3 {
  void member(int, int) {
    cout << "three" << endl;
  }
};

int main() {
  callback = f1;
  callback(0,0);
  callback = f2{};
  callback(0,0);
  f3 obj;
  callback = [&obj] (int a, int b) { obj.member(a,b); };
  callback(0,0);
  using namespace std::placeholders;
  callback = std::bind(&f3::member, obj, _1, _2);
  callback(0,0);
  return 0;  
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM