我在大学的c ++项目中遇到以下问题:
我想通过使用地图存储Class1的一些对象。
由于我的项目的设计,将地图保存为成员变量的类不会创建要存储在地图中的对象。我对这个论坛的研究告诉我使用unique_ptr来传递这些对象。
将这两个想法结合在一个实验测试项目中时:
#include <iostream>
#include <memory>
#include <unordered_map>
typedef std::unique_ptr<std::string> string_ptr;
class Class1 {
public:
std::unordered_map<std::string, string_ptr> my_unordered_map;
Class1() : my_unordered_map(){
}
void addTo(string_ptr ptr) {
std::string string = *ptr;
std::cout << string << std::endl;
my_unordered_map[0] = std::move(ptr);
}
};
int main() {
std::cout << "Process started!"<< std::endl;
string_ptr ptr;
ptr = std::make_unique<std::string>("text");
Class1 cont;
cont.addTo(std::move(ptr));
}
它编译,但抛出
在抛出'std :: logic_error'实例后终止调用 what():basic_string :: _ M_construct null无效
at runntime。
我也尝试按照其他帖子的建议将void addTo(string_ptr ptr)更改为addTo(string_ptr&amp; ptr),但问题仍然存在。
现在,问题是什么?是吗:
a)设计错误,不让Class1自己创建对象。在这种情况下,C++ inserting unique_ptr in map会回答我的问题
- 或 -
b)其他我对c ++的小知识让我想念?
旁注:我希望存储在这些指针中的对象不是字符串。
答案 0 :(得分:2)
您的问题与unique_ptr
无关。它根本与你的价值对象无关。它实际上是你的钥匙。不幸的是,整数文字0(并且只有0,而不是值为0的int变量)可以被视为任何类型的指针。而且不幸的是,std::string
有一个来自char const*
的隐式转换构造函数。所以当你这样做时:
my_unordered_map[0] = std::move(ptr);
由于您的密钥类型为std::string
,因此您隐式地从空指针构造std::string
。那是你的错误。
答案 1 :(得分:1)
下面
my_unordered_map[0] = std::move(ptr);
您将int
作为密钥传递,但my_unordered_map
期望std::string
为关键解决方案:
my_unordered_map[string] = std::move(ptr);
在抛出'std :: logic_error'的实例后终止调用 what():basic_string :: _ M_construct null无效
std::string
具有来自char const*
的隐式转换构造函数,它意味着尝试从NULL指针构造std::string
,这是导致此错误的原因。
如果您需要空字符串,请执行以下操作
my_unordered_map[std::string("")] = std::move(ptr);