gpt4 book ai didi

c++ - 如何强制始终首先删除给定资源?

转载 作者:塔克拉玛干 更新时间:2023-11-03 07:17:07 26 4
gpt4 key购买 nike

在我的项目中,我有一个事件系统。您可以将回调连接到事件,并且只要发送事件,就会调用您的回调。

连接到事件后,您将获得一个 token 。只要 token 没有被破坏,连接就处于事件状态:

class A
{

A()
{
event_connection = get_dispatcher().connect(event, std::bind(member_function, this));
}
void member_function()
{
dummy_instance++; //any action that uses this field
}
// changed from shared to unique to avoid confusion
//std::shared_ptr<event_connection_token> event_connection;
std::unique_ptr<event_connection_token> event_connection;
dummy_type dummy_instance;
}

但是,在下面的场景中出现了一个问题:

  1. A 类的解构开始
  2. 字段 dummy_instance 被销毁
  3. 现在事件发生
  4. 调用回调是因为 event_connection 尚未销毁
  5. 回调试图访问释放的内存,程序崩溃

因此,我需要我的 event_connection_token 始终在回调使用的任何类成员之前被销毁。现在,如果我想让 100 个其他程序员使用这个事件回调系统,那么期望他们总是在他们创建的所有类中首先释放 event_connection_token 是不专业的。我们终于来到了这个问题:

我如何强制每个客户端在客户端类中的任何其他内容被销毁之前删除 event_connection_token

我正在寻找:

  • 一个聪明的设计,可以确保 token 总是在程序员没有考虑的情况下首先被删除,或者
  • 编译时/运行时检查,让程序员知道他们需要修改代码,以便首先删除 token 。

编辑: 标记为重复的问题没有解决我的问题。我知道对象的销毁顺序,甚至在析构函数中显式调用 .reset() 都可以解决我的问题。然而,这不是解决我的问题的方法。问题是我不想依赖项目中的每个开发人员都记住这个规则(因为这个事件回调系统将在代码中的许多地方使用)。

最佳答案

只需交换声明

class A
{

A()
{
event_connection = get_dispatcher().connect(event, std::bind(member_function, this));
}
void member_function()
{
dummy_instance++; //any action that uses this field
}
// changed from shared to unique to avoid confusion
//std::shared_ptr<event_connection_token> event_connection;

dummy_type dummy_instance;
std::unique_ptr<event_connection_token> event_connection;
}

销毁顺序与声明顺序相反(因为构造是按声明顺序进行的)。现在销毁实例时,首先调用实例的析构函数,然后销毁 event_connection,最后销毁 dummy_instance(构造以相反的顺序发生)。

我认为如果你不想在阻止他们做“愚蠢”的事情上走得太远(我甚至不要认为您可以涵盖所有极端情况)。

如果你不能要求他们把 event_connection 放在最后,那么你必须禁止他们通过组合添加它(即使你添加它,你最终也会明确地要求他们删除指针)。这将首先排除 A 中的 event_connection,而只允许 event_connection 引用 A,如果您使用智能指针,它会很好地工作(除了这意味着只要 event_connection 保持不变,A 对象就会保持不变)。

关于c++ - 如何强制始终首先删除给定资源?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31993774/

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