![]() |
1
3
因此,如果所有插槽都与信号断开连接,第二次调用信号不会调用任何内容,但它应该清理插槽。 回答您的评论,是的,如果连接了其他插槽,再次调用信号是不安全的,因为它们将再次被调用。在这种情况下,我建议您反过来连接一个虚拟插槽,然后在调用“真实”插槽时断开它。连接另一个插槽将清除陈旧的连接,因此您的插槽应该被释放。 只需确保不要在虚拟插槽中保留任何需要释放的引用,否则就回到了开始的位置。 |
![]() |
2
2
|
![]() |
3
1
对于作用域_连接,行为是否更加严格? 因此,不是:
(复制品由
我没有使用过任何类型的信号,所以这更像是猜测,而不是跟踪
|
![]() |
4
1
我最终完成了自己的信号(子集)实现,主要要求是通过调用connection::disconnect()销毁插槽。 该实现沿着将所有插槽存储在从插槽实现指针到插槽实现的共享ptr(而不是列表/向量)的映射中的信号线进行,从而提供对单个插槽的快速访问,而无需迭代所有插槽。在我的例子中,插槽实现基本上是一个boost::函数。 连接对信号的内部实现类具有弱\u ptr,对插槽实现类型具有弱\u ptr,以允许信号超出范围,并将插槽指针用作信号映射中的键,以及指示连接是否仍处于活动状态(不能使用原始指针,因为这可能是错误的)重复使用)。 调用disconnect时,这两个弱指针都将转换为共享_ptr,如果这两个都成功,则要求信号实现断开指针给定的插槽。这是通过简单地从地图上删除它来完成的。
上述方法适用于我的场景,在我的场景中,感兴趣的信号很少被触发(在这种情况下只触发一次),但存在大量短期连接,否则即使使用问题中概述的技巧,也会消耗大量内存。 对于其他场景,我已经能够用boost::函数(因此要求只能有一个连接)来代替信号的使用,或者只是通过坚持解决侦听器自身管理其生命周期的问题。 |
![]() |
5
1
我偶然发现了同样的问题,我真的错过了API中的某种显式清理。 在我的场景中,我正在卸载一些插件dll,我必须确保在卸载的dll中没有引用代码(vftable或其他)的悬空对象(插槽)。由于延迟删除的原因,简单地断开插槽是不起作用的。 我的第一个解决方案是一个信号包装器,它稍微调整了代码:
不幸的是,这不起作用,因为
在没有其他选择的情况下,我最终修补了原作
这是我的boost 1.5.3补丁
|
![]() |
rookie · 检查函数模板的所有参数包参数是否属于int 1 年前 |
![]() |
ivaigult · -W转换和隐式字符串到布尔类型转换 1 年前 |
![]() |
rainer · 后台插入程序的初始化 1 年前 |
![]() |
Community wiki · 以理智、安全和高效的方式复制文件 1 年前 |
|
Shefali Kanaujia · 对C中向量的向量进行排序++ 1 年前 |
|
Ma Joonyoung · 粗粒度和细粒度链表的时间比较 1 年前 |