我想存储元素(让它称之为E),但我不知道我应该将它们存储为对象或指向动态分配对象的指针。
(A,B,C等对象存储所需E的引用)
版本A:
E e;
store.Add(e); //This time the store contains objects.
在此版本中,元素将被复制到商店,但它更容易处理。 (当销毁父对象时,对象将被销毁)
版本B:
E* e = new E();
store.Add(*e); //This time the store contains references.
/*I chose references instead of pointers,
so I have to use pointers only at allocating and deallocating.*/
在这个版本中没有复制构造。但我必须删除父对象的析构函数中的对象。
哪个更好,为什么?哪个会导致更多错误,哪个更有效?
答案 0 :(得分:2)
使用c ++ 11,你也可以直接在容器中构建它们:
std::vector<Widget> widgets;
widgets.emplace_back(/*Parameters to construct a widget*/);
哪个更好,为什么?
这取决于您的申请。如果容器应该拥有对象,并且复制起来不太昂贵,那么值语义会更容易。如果它们很容易复制,但很容易移动,标准容器将移动它们(你当然必须提供移动构造函数)。
通过存储智能指针,您还可以充分利用这两个方面。这样,如果需要,你就会得到多态性。
std::vector<std::unique_ptr<Widget>> widgets;
widgets.push_back(std::make_unique<Widget>(/*Parameters to construct a widget*/));
哪个会导致更多错误,哪个更有效?
第一个问题完全取决于你作为程序员的技能,第二个问题不能用一揽子声明来回答。程序需要进行基准测试并进行分析以提高效率。
答案 1 :(得分:2)
这取决于您如何使用商店。存储对象意味着您在调用Add
时以及在复制商店时(以及其他情况下)复制它们:这可能会产生成本,并可能导致不必要的行为。
指针可能是一个不错的选择,但您应该更喜欢托管指针,例如std::unique_ptr
,因此您不必处理删除。
版本C:
auto e = std::unique_ptr<E>(new E());
store.Add(e); //This time the store contains managed pointers.
如果您有C ++ 14可用,也可以使用std::make_unique
。
版本C bis:
auto e = std::make_unique<E>();
store.Add(e); //This time the store contains managed pointers.
如果您需要共享指向的对象,另一个选项可以是使用std::shared_ptr
,但只在需要时使用它。
版本D:
auto e = std::make_shared<E>();
store.Add(e); //This time the store contains shared managed pointers.