C++ C++;STL容器和引用

C++ C++;STL容器和引用,c++,stl,reference,C++,Stl,Reference,我对引用、STL容器和对象的工作方式有误解 我以前在STL容器中使用引用,但STL容器似乎是“存储对象的对象”。但是如果我想在容器中存储对象并修改它们,我该怎么做呢 我贴了一小段代码来说明我的问题 class MyObject { public : int value; MyObject(const MyObject& right) : value(right.value) {} MyObject(int _value) : value(_va

我对引用、STL容器和对象的工作方式有误解

我以前在STL容器中使用引用,但STL容器似乎是“存储对象的对象”。但是如果我想在容器中存储对象并修改它们,我该怎么做呢

我贴了一小段代码来说明我的问题

class MyObject {
    public : 
        int value;

    MyObject(const MyObject& right) : value(right.value) {}
    MyObject(int _value) : value(_value) {}

    bool operator< (const MyObject& right) const {
        return value < right.value;
    }

    void display() const {
        cout << "(" << value << ")  ";
    }
};
但我有以下错误:


错误:从“const MyObject”类型的表达式初始化“MyObject&”类型的引用无效。

您可以使用引用来分配给对象-通过将循环变量
o
设置为引用:

cout << "Increnting ... " << endl;
for (MyObject &o : oset)  o.value += 1000;
更安全的解决方案

将创建另一个集合,复制原始集合(同时应用所需的更改),然后将新集合替换为旧集合

此处
transform
将lambda函数应用于整个集合,并将结果存储在新的
nset
集合中<代码>插入器为nset容器创建插入迭代器,从nset.begin()插入。最后一个变换参数lambda获取一个原始的set对象,并向其添加1000,返回新对象。转换创建新集合后,
swap
将新对象放置在原始容器中

set<MyObject> nset;
transform(oset.begin(), oset.end(), inserter(nset, nset.begin()),
   [](const MyObject &o) { return MyObject (o.value+1000); });
oset.swap(nset);
设置nset;
转换(oset.begin(),oset.end(),插入器(nset,nset.begin()),
[](constmyobject&o){返回MyObject(o.value+1000);};
oset交换(nset);

有关更多信息,请参见上的此问题。

对于(MyObject o:oset)o.value+=1000,错误的行是

对于(MyObject&o:oset)o.value+=1000改为使用引用变量引用对象本身:

for (MyObject& o : oset)  
   o.value += 1000;

注意“&”,它使名称为“o”请参阅集合中的对象而不是复制。< / P>如果有这样的错误,我会从“const MyObjts”类型的表达式中看到“MyObjult&”类型的引用初始化无效。请注意,我没有一个C++ 11编译器来检查上面的代码片段。谢谢您的回答。- 1:迭代
oset
在修改其结构时?我想看看Valgrind有什么要说的。。。§6.5.4[stmt.range]表示您正在调用未定义的行为。如果有人仍感兴趣,则已修改解决方案。感谢Matthieu用原始解决方案指出问题。
// ===== ATTENTION - NASTY CODE ALERT !! ========**
    for (MyObject &o : oset)
    {
        MyObject oNew = o;
        oNew.value += 1000;
        oset.erase(o);
        oset.insert(oNew);
    }
// =============================================**
set<MyObject> nset;
transform(oset.begin(), oset.end(), inserter(nset, nset.begin()),
   [](const MyObject &o) { return MyObject (o.value+1000); });
oset.swap(nset);
for (MyObject& o : oset)  
   o.value += 1000;