【问题标题】:How to allocate a non-copyable and non-movable object into std::map?如何将不可复制且不可移动的对象分配到 std::map 中?
【发布时间】:2014-10-13 14:44:41
【问题描述】:

我有一个对象,我想限制它只能在std::map 内分配。这是简化的代码:

#include <map>

class Value
{
public:
    Value(int value) { _value = value;}
    Value(const Value&) = delete;
    Value& operator=(const Value&) = delete;
    Value(Value&&) = default;     // ***
    void* operator new(size_t) = delete;    // not on free store
private:
    int _value;
};

class Container
{    
public:
    Container();
    Value* addToMap(int key) {
        auto ret = _map.emplace(key, key);
        return &(ret.first->second);
    }
private:
    std::map<int, Value> _map;
};

为了让它在 Mac 上使用 CLang 编译,我必须添加一个用星号标记的行,请求默认移动构造函数。但是,在 Windows Visual Studio 中编译时,此行会导致 C2610 错误。看起来 VS2013 C++11 不合规包括无法生成默认移动构造函数。我是否有不同的方法可以在标准映射内分配一个可以跨平台编译的对象,还是我必须实现自己的移动构造函数?

【问题讨论】:

  • 为什么要添加这个限制?
  • 我希望该对象由容器独占,并防止其他代码调用new和delete。
  • 您正在混合对象和数据结构。如果您的数据结构的用户想要复制对象,为什么不呢?
  • 我的对象的性质是这样的,我不希望它们无法控制地复制或移动。我有一个由多种类型的相互依赖对象组成的网络,为了强制网络拓扑的有效性,我需要限制对象被激活和销毁的方式。从某种意义上说,我的原因类似于人们想要使用 unique_ptr 来存储他们的数据的原因。

标签: c++ c++11 move-semantics stdmap


【解决方案1】:

一个选项是使用std::piecewise_construct:

Value* addToMap(int key) {
    auto ret = _map.emplace(std::piecewise_construct
                          , std::forward_as_tuple(key)
                          , std::forward_as_tuple(key));
    return &(ret.first->second);
}

VC++ DEMO

【讨论】:

    猜你喜欢
    • 2023-04-10
    • 2014-12-15
    • 1970-01-01
    • 2020-12-05
    • 1970-01-01
    • 1970-01-01
    • 2014-03-10
    • 1970-01-01
    相关资源
    最近更新 更多