c ++回调到另一个成员函数
c++ callbacks to another member function
我有一个关于回调的问题。以前,我将我的回调关联到 class Q
class Q{
using Callback = std::function<void(char*, int)>;
Q:Q();
Q:~Q();
void Q::RegisterCB(Callback callbackfunc)
{
callback_func = callbackfunc;
}
void Q:someEvent()
{
callback_func();
}
};
void handleCallback( char*, int)
{
// perform some routine
}
// from my main file
int main()
{
Q q;
q.RegisterCB(&handleCallback);
}
对我来说效果很好。但是,当我需要将 handleCallback 函数转移到另一个 class 以获得更清晰的代码时。我在使用相同代码时遇到问题
class R{
void R::handleCallback( char*, int)
{
// perform some routine
}
void R::someOp()
{
// q is some member variables of R
q.RegisterCB(&R::handleCallback, this);
}
};
但是,我 运行 遇到了一些问题,说有一个“没有匹配的函数来调用......”。我认为这只是简单地从函数名分配给 class 函数名
我可以提示我哪里可能出错吗?
此致
&R::handleCallback
的类型为 void (R::*)(char*, int)
,无法转换为 std::function<void(char*, int)>
。
此外,RegisterCB
接受一个参数,而不是两个。
最直接的解决方法是将调用包装在 lambda 函数中,
q.RegisterCB([this](char* p, int x) { handleCallback(p, x); });
有关如何使用 lambda 函数将 R 实例的成员函数注册为事件处理程序的示例。 (出于习惯,我用 string_view 替换了 char* ,这对这个例子来说不是必需的)。建议尽可能使用“const”。
#include <functional>
#include <string_view>
#include <iostream>
class Q
{
public:
// use const arguments, the callback is not supposed to change them
// just passing information on to callback
using callback_t = std::function<void(const std::string_view&, const int)>;
// initialize callback with a (lambda) function that does nothing
// this prevents the need for a check if callback has been set or not
// (Pattern : Null Strategy)
Q() :
m_callback_func( [](const std::string_view&,const int) {} )
{
}
~Q() = default;
void RegisterCallback(callback_t fn)
{
m_callback_func = fn;
}
void Event(const std::string_view& string, const int value)
{
m_callback_func(string,value);
}
private:
callback_t m_callback_func;
};
void handleCallback(const std::string_view& string, const int value)
{
std::cout << string << ", " << value << "\n";
}
class R
{
public:
void handleCallback(const std::string_view& string, const int value)
{
std::cout << string << ", " << value << "\n";
}
};
// from my main file
int main()
{
Q q1;
q1.RegisterCallback(handleCallback);
q1.Event("Hello", 42);
// to pass a callback to an instance of a class
// you can use a lambda function https://en.cppreference.com/w/cpp/language/lambda
R r;
Q q2;
q2.RegisterCallback([&r](const std::string_view& string, const int value)
{
r.handleCallback(string,value);
});
q2.Event("World",21);
return 0;
}
我有一个关于回调的问题。以前,我将我的回调关联到 class Q
class Q{
using Callback = std::function<void(char*, int)>;
Q:Q();
Q:~Q();
void Q::RegisterCB(Callback callbackfunc)
{
callback_func = callbackfunc;
}
void Q:someEvent()
{
callback_func();
}
};
void handleCallback( char*, int)
{
// perform some routine
}
// from my main file
int main()
{
Q q;
q.RegisterCB(&handleCallback);
}
对我来说效果很好。但是,当我需要将 handleCallback 函数转移到另一个 class 以获得更清晰的代码时。我在使用相同代码时遇到问题
class R{
void R::handleCallback( char*, int)
{
// perform some routine
}
void R::someOp()
{
// q is some member variables of R
q.RegisterCB(&R::handleCallback, this);
}
};
但是,我 运行 遇到了一些问题,说有一个“没有匹配的函数来调用......”。我认为这只是简单地从函数名分配给 class 函数名
我可以提示我哪里可能出错吗?
此致
&R::handleCallback
的类型为 void (R::*)(char*, int)
,无法转换为 std::function<void(char*, int)>
。
此外,RegisterCB
接受一个参数,而不是两个。
最直接的解决方法是将调用包装在 lambda 函数中,
q.RegisterCB([this](char* p, int x) { handleCallback(p, x); });
有关如何使用 lambda 函数将 R 实例的成员函数注册为事件处理程序的示例。 (出于习惯,我用 string_view 替换了 char* ,这对这个例子来说不是必需的)。建议尽可能使用“const”。
#include <functional>
#include <string_view>
#include <iostream>
class Q
{
public:
// use const arguments, the callback is not supposed to change them
// just passing information on to callback
using callback_t = std::function<void(const std::string_view&, const int)>;
// initialize callback with a (lambda) function that does nothing
// this prevents the need for a check if callback has been set or not
// (Pattern : Null Strategy)
Q() :
m_callback_func( [](const std::string_view&,const int) {} )
{
}
~Q() = default;
void RegisterCallback(callback_t fn)
{
m_callback_func = fn;
}
void Event(const std::string_view& string, const int value)
{
m_callback_func(string,value);
}
private:
callback_t m_callback_func;
};
void handleCallback(const std::string_view& string, const int value)
{
std::cout << string << ", " << value << "\n";
}
class R
{
public:
void handleCallback(const std::string_view& string, const int value)
{
std::cout << string << ", " << value << "\n";
}
};
// from my main file
int main()
{
Q q1;
q1.RegisterCallback(handleCallback);
q1.Event("Hello", 42);
// to pass a callback to an instance of a class
// you can use a lambda function https://en.cppreference.com/w/cpp/language/lambda
R r;
Q q2;
q2.RegisterCallback([&r](const std::string_view& string, const int value)
{
r.handleCallback(string,value);
});
q2.Event("World",21);
return 0;
}