O que significa iterator-> second?

157

Em C ++, qual é o tipo de a std::map<>::iterator?

Sabemos que um objeto itdo tipo std::map<A,B>::iteratortem uma sobrecarga operator ->que retorna um std::pair<A,B>*, e que o std::pair<>tem firste secondmembro.

Mas, a que esses dois membros correspondem e por que precisamos acessar o valor armazenado no mapa como it->second?

Noich
fonte
14
A std::maparmazena uma chave e um valor . map::iterator.secondrefere-se ao valor .
usar o seguinte

Respostas:

247

Tenho certeza que você sabe que um std::vector<X>armazena um monte de Xobjetos, certo? Mas se você tem um std::map<X, Y>, o que ele realmente armazena é um monte de std::pair<const X, Y>s. É exatamente o que é um mapa - ele une as chaves e os valores associados.

Quando você itera sobre um std::map, você está iterando sobre todos esses std::pairs. Quando você desreferencia um desses iteradores, obtém um std::paircontendo a chave e seu valor associado.

std::map<std::string, int> m = /* fill it */;
auto it = m.begin();

Aqui, se você o fizer agora *it, receberá std::pairo primeiro elemento no mapa.

Agora, o tipo std::pairdá acesso a seus elementos através de dois membros: firste second. Portanto, se você tiver std::pair<X, Y>chamado p, p.firsté um Xobjeto e p.secondé um Yobjeto.

Portanto, agora você sabe que a desreferenciação de um std::mapiterador fornece a std::pair, então você pode acessar seus elementos com firste second. Por exemplo, (*it).firstvocê fornecerá a chave e (*it).secondo valor. Estes são equivalentes a it->firste it->second.

Joseph Mansfield
fonte
4
Por que eles simplesmente não usam [0] e [1] (para "primeiro" e "segundo") como tudo na programação?
21
@AdamCross Porque operator[]tem que retornar um tipo específico mas firste secondpodem ter tipos diferentes. Por outro lado, std::tuplepossui uma função auxiliar especial std::getpara acessar seus elementos por índice.
Joseph Mansfield
16

O tipo dos elementos de um std::map(que também é o tipo de uma expressão obtida desreferenciando um iterador desse mapa) cuja chave é Ke seu valor é Vis std::pair<const K, V>- a chave é constimpedir que você interfira na classificação interna dos valores do mapa.

std::pair<>tem dois membros nomeados firste second(veja aqui ), com um significado bastante intuitivo. Assim, dado um iterador ipara um determinado mapa, a expressão:

i->first

O que equivale a:

(*i).first

Refere-se ao primeiroconst elemento ( ) do pairobjeto apontado pelo iterador - ou seja, refere-se a uma chave no mapa. Em vez disso, a expressão:

i->second

O que equivale a:

(*i).second

Refere-se ao segundo elemento do pair- ie ao valor correspondente no mapa.

Andy Prowl
fonte
5
As palavras "chave" e "valor" teriam sido mais intuitivas que "primeiro" e "segundo", o que implica ordem.
ahoffer 5/09/18