gpt4 book ai didi

c++ - 将带有静态回调参数的 C 函数包装到接受私有(private)成员作为回调的 C++ 函数

转载 作者:行者123 更新时间:2023-11-28 06:05:54 27 4
gpt4 key购买 nike

我想包装这个 C 函数,

int sqlite3_exec(
sqlite3*, /* An open database */
const char *sql, /* SQL to be evaluated */
int (*callback)(void*,int,char**,char**), /* Callback function */
void *, /* 1st argument to callback */
char **errmsg /* Error msg written here */
);

在 C++ 函数中,例如,

namespace
IronMaiden
{
int
BookOfSouls::MyWrapper( DB* db
, std::string& sql
, ?? callback function ?? int (*callback)(void*,int,char**,char**) ?? )
{
.
.
.
sqlite3_exec( db->get(), sql.c_str(), ?? callback ??, nullptr, nullptr);
.
.
.
}
}

我可以将任何静态函数传递给 sqlite3_exec(),但我想从 BookOfSouls 对象传递一个私有(private)成员函数作为回调函数,并且我想访问来自该函数的对象的私有(private)数据。

最佳答案

关键是 void* 参数:

int (*callback)(void*,int,char**,char**),  /* Callback function */
void *, /* 1st argument to callback */

回调是一个自由函数,但您可以提供任意第一个参数。因此,如果您想传入成员函数,我们可以利用无捕获 lambda 可转换为函数指针这一事实(感谢 some sorcery ):

template <typename F, int (F::*mem)(int, char**, char**)>
void set_callback(F* f) {
sqlite3_exec(db->get(), sql.c_str(),
+[](void* arg, int i, char** p, char**q){
return (static_cast<F*>(arg)->*mem)(i, p, q);
},
f,
nullptr, nullptr);
}

请注意,成员函数也必须是模板参数,这样 lambda 就不必捕获。如果您只需要一个特定的函数名称,它会更简单,例如sqlCallback(),那么你的回调函数将是:

+[](void* arg, int i, char** p, char** q) {
return static_cast<F*>(arg)->sqlCallback(i, p, q);
}

关于c++ - 将带有静态回调参数的 C 函数包装到接受私有(private)成员作为回调的 C++ 函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32415873/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com