Как изменить значения ключей в контейнере std:: map
дано
std::map<int,std::string> myMap;
fillMyMapWithStuff(myMap);
// modify key values - I need to add a constant value to each key
for (std::map<int,std::string>::iterator mi=myMap.begin(); mi != myMap.end(); ++mi)
{
// ...
}
какой хороший способ применить некоторую переиндексацию? Надо удалить старую запись и добавить новую с новым ключом и старое значение?
5 ответов
Похоже, вам лучше построить новую карту и поменять ее после этого. У вас будет только n
операции вставки вместо n
удаление и n
вставок.
да, вам придется удалить старую запись и добавить новую с новым ключом. Ключи не изменяются.
если бы вы изменяли только один или несколько элементов, вы могли бы сделать это эффективно, намекая map::insert
с положением нового элемента. Так как ваши новые ключи обязательно должны быть где-то после старые ключи, вы можете намекнуть с итератором, который указывает на старый элемент. Однако вам придется позаботиться о том, чтобы не переоценить недавно вставленные ключи (by например, итерация от конца к началу), и в случае изменения всей карты более эффективно просто построить новую.
Я думаю, вам придется строить новую карту. Если вы удалите и добавите новые ключи в цикле, это может разрушить целостность итерации по набору старых ключей и не касаясь только что вставленных ключей. (Если вы не знаете, как распределяются ваши ключи и не помещаете туда свою собственную логику.)
std::map<int,std::string> myMap;
fillMyMapWithStuff(myMap);
std::map<int,std::string> newMap;
// modify key values - I need to add a constant value to each key
for (std::map<int,std::string>::iterator mi=myMap.begin(); mi != myMap.end(); ++mi)
{
newMap[mi->first] = mi->second;
}
есть еще один вариант. Если эта операция является важной особенностью вашей коллекции и важна производительность, вы можете вообще избежать копирования карты. Вы можете создать класс перегрузки operator[]
, а также другие аксессоры и мутаторы, и добавить текущий сдвиг значения ключа.