2015-08-07 3 views
0

У меня есть карта, которая выглядит какСтирание вложенной элементы карты

typedef std::map<int, std::set<float>> innerMap; 
typedef std::map<long, innerMap> outerMap; 

Я хочу сделать следующее:
1. Я хочу, чтобы удалить внутренние элементы карты для ключа внешней карты.
2. Затем я хочу стереть внешний ключ карты, если он содержит 0 внутренних элементов карты.

Для первого сценария, я написал код, как:

outerMap mapA; 
//assuming this map contain an element 
//longx is key in outer element, intx is key of inner element 
std::map<int, std::set<float>>::const_iterator innerIter = mapA[longx].begin(); 
while (innerIter != mapA[longx].end()) 
{ 
    if (innerIter->first == intx) 
    { 
    if (innerIter->second.size() == 0) 
    { 
     mapA[longx].erase(innerIter++); 
    } 
    break; 
    } 
    ++innerIter; 
} 

Я написал этот код в C++, но я хочу использовать C++ 11. Можем ли мы написать это лучше в C++ 11?

Для второго сценария мне нужно снова повторить внешнюю карту и проверить ее элементы значений, или я могу сделать это в существующем коде?

+2

Возможно, вам действительно нужно 'std :: multimap'? – Hcorg

+0

Вы когда-нибудь удаляли более одного элемента из innerMap? Код кажется, что он только удаляет один элемент, я не совсем понимаю, зачем вам нужен цикл для этого. – bennofs

+0

@Hcorg, это хороший момент, я изучу multimap для моих требований. – Nipun

ответ

0

Этот код выглядит слишком сложно для меня. Следующее должно сделать то же самое, не нужно использовать необычные возможности C++ 11:

outerMap mapA; 

// Lookup iterator for element of outerMap. 
outerMap::iterator const outerIter = mapA.find(longx); 

// Lookup iterator for element of innerMap that should be checked. 
innerMap::const_iterator const innerIter = outerIter->second.find(intx); 

// Check if element of innerMap should be erased and erase it if yes. 
if(innerIter != outerIter->second.end() && innerIter->second.size() == 0) { 
    outerIter->second.erase(innerIter); 
} 

// Erase element of outer map is inner map is now empty: 
// This should do scenario 2 
if(outerIter->second.size() == 0) { 
    mapA.erase(outerIter); 
} 
0

, что вы делаете в данный момент (в C++ 11):

auto& inner = mapA[longx]; 
const auto it = inner.find(intx); 
if (it != inner.end() && it->second.size() == 0) { 
    inner.erase(it); 
} 
+0

Во второй строке это будет найдено (intx), а не find (it.x). его опечатка. – Nipun

+0

@Nipun: спасибо, опечатка исправлена. – Jarod42

+0

Кроме того, этот код не делает то же, что и код в вопросе: код в вопросе удаляет элемент из 'inner', а не из' mapA'. (Он вызывает 'mapA [longx] .erase (innerIter ++)'). Однако трудно догадаться, что должен делать код в вопросе, поскольку он содержит ошибки компиляции. – bennofs

Смежные вопросы