gpt4 book ai didi

c++ - 试图为成员(member)回拨

转载 作者:行者123 更新时间:2023-11-30 03:22:13 25 4
gpt4 key购买 nike

我有课 stickyNotes , 在其中我有函数 addNote这是一个公共(public)非静态函数。在代码中定义了一个新类型: typedef void(*fptr)

我还有课Button它在其构造函数中采用类型为 fptr 的变量, 我有一个函数 makeButton()返回 Button对象。

stickyNotes还有另一个成员叫rendermainWindow它呈现主窗口并添加一个按钮,我正在尝试创建一个类型为 fptr 的新变量设置为 stickyNotes::addNote 的地址我得到了错误:

'&': illegal operation on bound member function expression

stickyNotes::rendermainWindow :

void stickyNotes::rendermainWindow() {
/*
Renders the main window
*/
this->buttonList.empty(); // buttonList is a list of all buttons
mainWindow->clear(sf::Color(29, 29, 27, 255)); // clearing the window
sf::Vector2u windowDimensions = mainWindow->getSize(); // getting window dimensions
fptr cb = &this->addNote; <-------- ERROR HERE
Button plusB = makeButton((int)(windowDimensions.x * 0.75),
(int)(windowDimensions.y * 0.15),
(int)(windowDimensions.x * 0.85),
(int)(windowDimensions.y * 0.25),
mainWindow,
cb);
// first button to add stuff
std::vector<Button> vect;
vect.push_back(plusB);
this->buttonList.push_back(vect);
renderNotes();

}

我尝试过的:

替换 this->addNotestickyNotes::addNote .

附言:

我不想让 addNote 成为静态的。而我想保持公开,如何制作一个带有addNote回调函数的按钮?如果有解决方法,我将很高兴听到。

最佳答案

您正在尝试将回调传递给按钮。如果您要求回调是一个简单的函数指针(不接收任何参数),那么您的回调不能保留任何状态

但是,所有非静态成员函数都需要至少一个状态才能被调用:它们需要知道在哪个对象中工作。

这两者从根本上是不一致的:如果您的按钮采用简单的函数指针,则它不能用于调用成员函数(抛开诸如全局状态之类的可怕技巧)。

解决此问题的一种方法是使用成员函数指针:它们指定它们在哪个类上运行(即是其成员函数)并且必须在该类的实例上调用。由于您可能希望按钮回调可用于多个类,因此您可以使用多态 - 这是 SHR 建议的接口(interface)解决方案。

按钮界面的另一个选项是获取(并存储)std::function<void()>而不是你的函数指针。 std::function可以存储状态并且非常方便地与 lambda 函数一起使用:

Button plusB = makeButton(/* ... */, [this]() { addNote(); });

最后,您可以允许用户将一些“自定义数据”传递到按钮界面,可能是 void*std::any传递给回调。然后用户可以存储例如stickyNotes该自定义数据中的实例。这与简单的函数指针兼容。但是,这种方法规避了类型安全并且非常低级。它在某些库中使用,因为它非常通用,但使用起来比 std::function 更烦人。方法。

关于c++ - 试图为成员(member)回拨,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/51305146/

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