调用 list.clear() 时出现运行时错误
Posted
技术标签:
【中文标题】调用 list.clear() 时出现运行时错误【英文标题】:runtime error when the list.clear() was called 【发布时间】:2013-12-16 13:32:42 【问题描述】:我想用 C++ 在 Windows 编程中模拟 C# 事件驱动编程。
我想以这种方式完成:
-
使用列表容器保存函数指针
重写+=操作符,使Event类可以在里面添加函数
这样 event+=handlerFuncName
重写 () 操作符,这样我们就可以调用列表中的函数了
事件类:
template<class Sender_Type, class Args_Type>
class Event
private:
typedef void(*HFUN)(Sender_Type *, Args_Type);
list<HFUN> handlers;
public:
void operator +=(HFUN handler)
handlers.push_back(handler);
void operator ()(Sender_Type *sender, Args_Type e)
for (list<HFUN>::iterator it = handlers.begin(); it != handlers.end(); it++)
(*it)(sender, e);
~Event() printf("Release..\n");
;
这是一个例子:
EventArgs 类和窗口类的定义:
class EventArgs ;
class Win32Window
public:
// event definition
Event<Win32Window, EventArgs> Loaded;
// ctor
Win32Window()
// ...
// trigger the Loaded event
Loaded(this, EventArgs());
// ...
;
事件处理函数的定义:
void Window_Loaded(Win32Window *sender, EventArgs e)
MessageBox(NULL, "Window_Loaded", "xx", 0);
主要功能:
Win32Window wnd;
//add the event handler function
wnd.Loaded += Window_Loaded;
它可以工作,但是当窗口关闭时,list.clear()
出现运行时错误!
这是一个snapshot 的异常:
【问题讨论】:
看不到你的图片... 什么是 HFUN?您能否显示初始化和清除此列表的代码,事件处理程序代码的问题不是必需的。请尝试将其减少到SSCCE。 成员函数指针显然不是答案。尝试阅读 Functors。 typedef void(*HFUN)(Sender_Type *, Args_Type);我还没有调用 clear() 函数。我认为它是在列表发布时自动调用的。对列表(处理程序)的所有操作都显示在这些代码中,不再有任何操作。 使用std::function
肯定会让这更容易阅读......而且更安全
【参考方案1】:
我认为,这正是std::function
旨在帮助解决的问题。为初学者尝试这样的事情:
#include <functional>
#include <iostream>
#include <vector>
template <typename Sender, typename... Args>
class Event
using FuncType = std::function<void(Sender&, Args...)>;
std::vector<FuncType> vec;
public:
Event& operator+=(FuncType f)
vec.push_back(f);
return *this;
void operator()(Sender& s, Args... a)
for (auto& f : vec)
f(s, a...);
;
struct Window
Event<Window, int, int> resized;
void resize(int width, int height)
// blah blah
resized(*this, width, height);
;
int main()
Window w;
w.resized += [](Window&, int w, int h)
std::cout << "Window resized to " << w << " by " << h << std::endl;
;
w.resize(800, 600);
请注意,此方法不仅允许您使用常规函数作为事件处理程序,还可以使用 lambda(如演示)和函数对象。
【讨论】:
非常感谢。这对我很有帮助。以上是关于调用 list.clear() 时出现运行时错误的主要内容,如果未能解决你的问题,请参考以下文章
使用 torch.load 时出现运行时错误“存储大小错误:”
运行 Oracle 调度程序时出现错误:ORA-20001:必须从应用程序会话中调用此过程