问题描述
我一直在绞尽脑汁,在声明,定义和最终调用程序内部的成员函数指针时正确使用语法。
I've been racking my brain over getting the syntax right on declaring, defining and finally calling a member function pointer inside my program.
我正在编写一个Xlib的窗口管理器,并试图使用户能够在 Keybind
s向量中定义所有键绑定。 Keybind
结构包含更多成员变量,为简洁起见,在此省略了它们。
I'm writing a window manager with Xlib, and am trying to enable the user to define all key bindings in a vector of Keybind
s. The Keybind
struct contains more member variables, which I have left out here for the sake of brevity.
这是什么我到目前为止为止。
Here's what I've got so far.
Keybind
,一个包含成员变量的结构func
,它指向 MyClass
成员函数。
Keybind
, a struct containing a member variable, func
, that points to a MyClass
member function.
struct MyBind {
MyBind(void (MyClass::*_func)(const XKeyEvent&))
: func(_func) {}
void (MyClass::*func)(const XKeyEvent&);
}
向量的声明和填充
包含用户定义的 Keybind
s。
Declaration and populating of a vector
that holds user-defined Keybind
s.
// in my_class.hh
std::vector<MyBind*> my_binds_;
// in my_class.cc, constructor
my_binds_.push_back(new MyBind( &MyClass::do_this ));
my_binds_.push_back(new MyBind( &MyClass::do_that ));
此时,所有内容都会编译并运行。
At this point, everything compiles and runs.
现在,当我尝试通过遍历 my_binds _
向量委派工作时,事情出了问题。值得注意的是,为了清楚起见,我省略了错误处理和其他成员变量访问。
Now, when I try to delegate work by iterating over the my_binds_
vector, things go wrong. It is worth noting that I've left out error handling and other member variable accesses for clarity.
void
MyClass::handle_input(const XKeyEvent& e)
{
for (const MyBind* my_bind: my_binds_) {
(my_bind->*func)(e); // erroneous line
}
}
此,但编译失败,并指出 error:'func在此范围内未声明'
( g ++
,与 clang ++
类似的错误)。
This should be the correct syntax, but it fails to compile, stating error: ‘func’ was not declared in this scope
(g++
, similar error from clang++
).
这对我来说很奇怪,因为用 auto test = keybind-&f; func;替换了错误的代码行;
可以编译。
This is weird to me, as replacing the erroneous line of code with auto test = keybind->func;
does compile.
我在做什么错?有没有更好的方法来处理用户键绑定定义?谢谢!
What am I doing wrong? Is there a better way to handle user key bind definitions? Thanks!
推荐答案
最好使用并完全忘记了原始成员函数指针。它们只会给您带来痛苦:)
It would be best to use std::function and forget about raw member-function pointers altogether. They will only bring you pain :)
代码的问题在于,您只有一个指向方法的指针,而没有对象。您的绑定结构还应该存储一个对象指针,以在以下位置调用该方法:
The problem with you code is that you only have a pointer to a method but no object. Your bind struct should also store an object pointer to call the method on:
struct MyBind {
MyBind(MyClass *obj, void (MyClass::*_func)(const XKeyEvent&))
: obj(obj), func(_func) {}
MyClass *obj;
void (MyClass::*func)(const XKeyEvent&);
void operator()(const XKeyEvent& event) const
{
(obj->*func)(event);
}
}
然后像这样使用它:
void
MyClass::handle_input(const XKeyEvent& e)
{
for (const MyBind* my_bind: my_binds_) {
(*my_bind)();
}
}
我在绑定结构中添加了一个调用运算符为了方便。请注意,-> *
运算符应用于该方法所属的对象。
I've added a call operator to the bind struct for convenience. Note that the ->*
operator is applied to the object the method belongs to.
这篇关于无法调用结构内部的成员函数指针的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!