共享通过智能指针拥有的对象

时间:2018-11-07 17:07:06

标签: c++ oop smart-pointers

基本上我有一个结构,其中包含要在类之间共享的对象,如下所示;

jar {
  exclude("**/*.class")
  from ("$buildDir/generated-files-dir")
}

在我的主班上,我通过 unique_ptr ;

拥有它
struct CoreComponents
{
    std::unique_ptr<a> m_A = std::make_unique<a>();
    std::unique_ptr<b> m_B;
    std::unique_ptr<c> m_C = std::make_unique<c>();
};

然后我还有其他的 n 类,需要从其功能访问该 m_Components 对象而不创建副本。 (我不会修改该对象的内容)

我尝试使用 shared_ptr Game 类中保存 m_Components ,然后通过通过值将其传递给其他类(传递给其构造函数)并进行存储,但是这种情况会导致内存泄漏。 (我使用memcheck来检查泄漏)我发现这是造成泄漏的原因,但我不知道到底是为什么。

Shared_ptr场景

我需要访问CoreComponents对象的类的构造方法;

class Game
{
    ...
  private:
    std::unique_ptr<CoreComponents> m_Components;
    ...
};

我试图将其保留为GameScene类的成员,然后在函数中使用它;

GameScene::GameScene(std::shared_ptr<CoreComponents> components)
: m_Components(std::move(components))

这就是我从Game类内部传递它的方式;

std::shared_ptr<CoreComponents> m_Components;

GameScene类内部的常规用法;

auto gs = std::make_unique<GameScene>(m_Components)

那么,使用现代c ++创建相似设计的最佳方法是什么? 我试图避免使用Singleton模式,但是我必须使用它来实现这一点吗?还是可以更好地使用智能指针?

PS:销毁Game类时,需要从内存中删除CoreComponents结构。

2 个答案:

答案 0 :(得分:1)

如果您确实拥有共享对象,最好的方法是使用shared_ptr

unique_ptr用于唯一所有权。

如果您有内存泄漏,那么该是调查原因的原因了,并修复它们!您的报告建议提供周期性参考。检查意外的lambda捕获,在某些地方,您可能打算改用weak_ptr

为此使用单身人士就像通过将整件东西着火并换上驴子来修理汽车的破轮胎一样。您的unique_ptr方法更像是通过拆下轮胎破损轮胎并在轮辋上行驶来修复轮胎破损。

答案 1 :(得分:1)

似乎您已正确区分了所有权使用的关注点。唯一的麻烦是如何将组件转发到系统的其余部分。

我会保留您的所有权结构,并为特定用户创建专用结构:

struct CoreComponents {
   unique_ptr<A> a; unique_ptr<B> b; ...
};

struct PartOfTheSystem {
  void use(A& a, B& b);
};

struct Game {
  CoreComponents components;
  PartOfTheSystem user;

  void stuff() {
    user.use(*components.a, *components.b);
  }
};

是的:更多键入内容。

而且:逻辑非常清晰:构造/所有权和使用是单独的关注点,而从设计上看这是完全清楚的!另请参阅https://isocpp.github.io/CppCoreGuidelines/CppCoreGuidelines#Rr-smartptrparam