【问题标题】:How to pass shared_ptr to naked ptr function如何将 shared_ptr 传递给裸 ptr 函数
【发布时间】:2012-09-27 12:53:24
【问题描述】:

我有一个由 lib 定义的 Entity 类,Registry 是管理使用地图注册到它的实体的类。

我想做什么:

//Registry Signature
void Registry::add(Entity* entity);


//my function (IGameEntity subclasses Entity)
void GameLogic::addEntity(shared_ptr<IGameEntity> entity, GameEntityId id) {
 GameEntityId entityId = entity->getId();
 gameEntities.push_back(entity);
 Framework::Registry::instance()->add(entity); //<-- this doesn't work
}

我试图弄清楚如何处理这个问题,因为我保留了 shared_ptr,然后我将不得不传递一个指针。

另一件事是,如果注册表因某种原因被破坏,它将在地图中剩余的所有实体上调用delete

如果我通过 entityweak_ptr&lt;Entity&gt;(entity) 它可以工作,但我并没有完全掌握如果 Registry 在weak_ptr 上调用 delete 会发生什么。

如果我通过entityentity.get() 当引用计数达到零或注册表试图删除它时会发生什么。

【问题讨论】:

  • 你完全陷入了僵局,因为你的设计是矛盾的。 shared_ptr 非常明确和有目的地拥有该资源。注册表需要使用它(幸运的是,您已经在使用shared_ptr,所以这很容易),或者根本不声明所有权。无论哪种方式,它调用delete 的事实都是问题所在。
  • 您显然需要定义您的所有权语义。您说Registry 管理 实体,但是,您的GameLogic 似乎也将shared_ptrs 存储到这些实体。

标签: c++ memory-management shared-ptr ownership


【解决方案1】:

您有两个不兼容的所有权方案。

您需要更改其中一个,或者克隆应该从一个方案转移到另一个方案的对象。

当对象只有一个引用时,有一个技巧可以释放shared_ptr。但你不想那样做。即使您对图书馆的内部有足够的了解也可以这样做。

因此,作为一个实用的解决方案,更改注册表。

让它接受shared_ptr

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2012-08-13
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-03-22
    • 1970-01-01
    • 2013-08-02
    相关资源
    最近更新 更多