从具有重复键的多图中仅删除一个元素

时间:2012-08-21 19:54:06

标签: c++ for-loop iterator multimap

我有一个带有Note对象的多图,我想从中删除一个对象。可以有多个具有相同键的Note对象。问题是,现在还有一些被删除的对象不在我指定的关键范围内:

long key = note.measureNumber * 1000000 + note.startTime; // = 2000001
multimap<long, Note>::iterator it;
for (it = noteList.lower_bound(key); it != noteList.end() && it->first < (key + 1); it++) {
    if(it->second.frequency == note.frequency){
        noteList.erase(it);
    }
}

当我使用键2000001运行此代码时,我能够擦除正确的对象,但另一个键1000017的对象也会被删除。两个对象的频率相同。

我的for循环有什么问题?

编辑:要清楚,我只想检查具有一个特定键的对象(在本例中为2000001),迭代器不需要查看具有不同键的对象。

3 个答案:

答案 0 :(得分:2)

使用迭代器调用erase()会使其无效,因此您无法继续使用它。

请参阅Can I continue to use an iterator after an item has been deleted from std::multimap<>

答案 1 :(得分:1)

擦除迭代器后,它将变为无效。如果您希望在迭代时从地图中删除,则需要更改代码。试试这个:

multimap<long, Note>::iterator it;
for (it = noteList.lower_bound(key); it != noteList.end() && it->first < (key + 1);) {
    if(it->second.frequency == note.frequency){
        noteList.erase(it++);
    }
    else
    {
        ++it;
    }
}

答案 2 :(得分:0)

如前所述,擦除迭代器会使其无效。 我想指出你所拥有的代码效率低下: 您不需要迭代直到循环结束。考虑一下:

for (it = noteList.lower_bound(key); it != noteList.upper_bound(key) && it->first == key; it++)
{
    if(it->second.frequency == note.frequency)
    {
       noteList.erase(it++);
    }
    else
    {
        ++it;
    }
}