我似乎无法弄清楚这一点,并尝试了以下建议:
Move `unique_ptr`s between sets
how to move an std::unique_ptr<> from one STL container to another?
我有两组包含唯一指针:
std::set<std::unique_ptr<some_type>> s1, s2;
指针当然是唯一的,但some_type的值可能是也可能不是,所以在将s2连接到s1之后,s1的大小可以与| s1 + s2 |相同或大。
似乎我应该能够做到这一点:
move(s2.begin(), s2.end(), inserter(s1, s1.end()));
但这与clang ++ 3.8 / g ++ 5.4失败了。
这里缺少什么?
答案 0 :(得分:3)
它不起作用,因为std::set
仅允许const
访问其元素。没有办法从std::set
移出一些东西。见Is it possible to move an item out of a std::set?
在C ++ 14中没有很好的方法可以做到这一点,但在C ++ 17中,为此提供了一个merge
方法,它只是重新排列数据结构的内部指针而无需复制或移动任何元素:
s1.merge(s2);
C ++ 14中一个稍微合理的解决方法是将std::set<std::unique_ptr<T>>
更改为std::map<T*, std::unique_ptr<T>>
。然后你可以这样做:
while (!s1.empty()) {
s2[s1.begin()->first] = std::move(s1.begin()->second);
s1.erase(s1.begin());
}
答案 1 :(得分:2)
目前,您将集合成员资格与所有权混为一谈,这就是问题的根源。
解决方案:使用多组原始指针,并将所有权移至其他位置。
重新设想的
const Example = Parse.Object.extend('example_table');
const Table1 = Parse.Object.extend('table1');
const table1Ptr = new Table1().set('objectId', '1');
const Table2 = Parse.Object.extend('table2');
const table2Ptr = new Table2().set('objectId', '6');
const addNewExample = function addNewExample(table1Ptr, table2Ptr) {
// return the promise that results from the save
return new Example() // just chaining everything to be terse...
.set('table1_id', table1Ptr)
.set('table2_id', table2Ptr)
.save(null, { useMasterKey: true }) // may not be necessary, depending
//
// don't use these old style handlers, use promise syntax
// which I substitute for the following below.
// success: function () {
// console.log('New object created');
// },
// error: function (error) {
// console.log('Failed to create new object');
// }
.then(
// fancy fat arrow notation for functions like the cool kids...
o => console.log('new object: ' + o.id + ' created'),
e => console.error('uh oh: ' + e.message)
);
};
addNewExample(table1Ptr, table2Ptr);
在标准库中move(s2.begin(), s2.end(), inserter(s1, s1.end()));
只是一个美化的演员,它不是一个动作例程。命令式名称形式具有误导性。将move
视为std::move
。
答案 2 :(得分:1)
在C ++ 17中,您可以使用std::set::merge
执行您想要的操作,如下例所示:
std::set<std::unique_ptr<T>> s1, s2;
...
s1.merge(s2);
C ++ 11的解决方法相当昂贵,而且有点背叛unique_ptr
的概念,这也需要你的对象是可复制的。将要复制您要在第一组中插入的新std::set
中的第二个std::unique_ptr
的对象:
std::set<std::unique_ptr<T>> s1, s2;
...
for(auto &&e : s2) {
s1.insert(std::make_unique<T>(*e));
}
s2.clear();
请注意,最后你需要clear
你的第二套才能从std::unique_ptr
概念的狂野分离引起的视频群聊中恢复过来。