普通的C++成员函数都隐含了一个传递函数作为参数,亦即“this”指针;
与类相关的回调函数要注意,类成员函数,如果是非静态,是带有this指针的,会与函数指针的类型不一致(无this),所以需要使用static函数,或者使用bind(&class::handler,this,_1)
1.普通函数方式
不使用成员函数,直接使用普通C函数,为了实现在C函数中可以访问类的成员变量,可以使用友元操作符(friend),在C++中将该C函数说明为类的友元即可。这种处理机制与普通的C编程中使用回调函数一样;
class AA {
private:
friend void sdk_core_on_data(qxwz_uint32_t type, const qxwz_void_t *data, qxwz_uint32_t len);
}
void sdk_core_on_data(qxwz_uint32_t type, const qxwz_void_t *data, qxwz_uint32_t len){}
sdk_config.data_cb = sdk_core_on_data;
但要注意,如果sdk_core_on_data需要用到类的其他变量或方法,还是要获取类实例;可使用单例模式或静态变量、方法;
友元函数只是说可以访问类的私有成员,与普通函数基本一样;
2. 静态函数方式
静态成员函数不使用this指针作为隐含参数,这样就可以作为回调函数;但回调函数所用到的变量都要是静态的;
3. bind函数方式
CallBack.h
#ifndef CALLBACK_H
#define CALLBACK_H
#include <stdio.h>
#include <functional>
template <typename T>
struct Callback;
template <typename Ret, typename... Params>
struct Callback<Ret(Params...)> {
template <typename... Args>
static Ret callback(Args... args) { return func(args...); }
static std::function<Ret(Params...)> func;
};
// Initialize the static member.
template <typename Ret, typename... Params>
std::function<Ret(Params...)> Callback<Ret(Params...)>::func;
#endif // CALLBACK_H
void SdkCoreInterface::sdk_core_on_start(qxwz_int32_t status_code, qxwz_uint32_t cap_id)
{
printf("zwh sdk_core_on_start, cap_id:=%d,status_code=%d \n", cap_id, status_code);
}
Callback<void(int)>::func = bind(&SdkCoreInterface::sdk_core_on_status, this, placeholders::_1);
sdk_config.status_cb = static_cast<qxwz_sdk_status_callback_t>(Callback<void(int)>::callback);
参考链接
https://blog.csdn.net/hyp1977/article/details/51784520
https://blog.csdn.net/zzhangjiej/article/details/4527662
https://www.cnblogs.com/dankye/archive/2012/08/25/2655816.html
https://oomake.com/question/174935
https://www.iteye.com/blog/socol-1826845
https://www.itranslater.com/qa/details/2583785166095254528
https://www.cnblogs.com/dahai/archive/2011/04/15/2017208.html
https://blog.csdn.net/weixin_44537992/article/details/105647556
https://www.codenong.com/19808054/