El siguiente código dice que pasar el mapa como const
en el operator[]
método descarta los calificadores:
#include <iostream>
#include <map>
#include <string>
using namespace std;
class MapWrapper {
public:
const int &get_value(const int &key) const {
return _map[key];
}
private:
map<int, int> _map;
};
int main() {
MapWrapper mw;
cout << mw.get_value(42) << endl;
return 0;
}
¿Esto se debe a la posible asignación que se produce en el mapa de acceso? ¿No se pueden declarar const funciones con accesos al mapa?
MapWrapper.cpp:10: error: passing ‘const std::map<int, int, std::less<int>, std::allocator<std::pair<const int, int> > >’ as ‘this’ argument of ‘_Tp& std::map<_Key, _Tp, _Compare, _Alloc>::operator[](const _Key&) [with _Key = int, _Tp = int, _Compare = std::less<int>, _Alloc = std::allocator<std::pair<const int, int> >]’ discards qualifiers
Respuestas:
std::map
'soperator []
no se declara comoconst
, y no puede deberse a su comportamiento:Como resultado, su función no se puede declarar
const
y usar el mapaoperator[]
.std::map
Lafind()
función de le permite buscar una clave sin modificar el mapa.find()
devuelve uniterator
, oconst_iterator
un questd::pair
contiene tanto la clave (.first
) como el valor (.second
).En C ++ 11, también puede usar
at()
parastd::map
. Si el elemento no existe, la función lanza unastd::out_of_range
excepción, a diferencia deoperator []
.fuente
operator[]
(por ejemplofoo[bar] = baz
) y rvalueoperator[]
(por ejemplox = foo[bar]
); este último ciertamente podría ser constante.Dado
operator[]
que no tiene una sobrecarga calificada const, no se puede usar con seguridad en una función calificada const. Probablemente esto se deba a que la sobrecarga actual se creó con el objetivo de devolver y establecer valores clave.En su lugar, puede utilizar:
o, en C ++ 11, puede usar el
at()
operador:fuente
map.find(KEY)->second;
no es seguro cuando los valores del mapa son cadenas. Tiende a imprimir basura cuando no se encuentra la CLAVE.No se puede usar
operator[]
en un mapa que esconst
porque ese método no lo es,const
ya que le permite modificar el mapa (puede asignarlo_map[key]
). Intente usar elfind
método en su lugar.fuente
Algunas versiones más nuevas de los encabezados GCC (4.1 y 4.2 en mi máquina) tienen funciones miembro no estándar map :: at () que se declaran const y lanzan std :: out_of_range si la clave no está en el mapa.
A partir de una referencia en el comentario de la función, parece que se ha sugerido como una nueva función miembro en la biblioteca estándar.
fuente
Primero, no debería usar símbolos que comiencen con _ porque están reservados para la implementación del lenguaje / escritor del compilador. Sería muy fácil que _map sea un error de sintaxis en el compilador de alguien, y no tendrías la culpa a nadie más que a ti mismo.
Si desea utilizar un guión bajo, colóquelo al final, no al principio. Probablemente cometió este error porque vio algún código de Microsoft haciéndolo. Recuerde, ellos escriben su propio compilador, por lo que pueden salirse con la suya. Aun así, es una mala idea.
el operador [] no solo devuelve una referencia, sino que crea la entrada en el mapa. Entonces, no solo está obteniendo un mapeo, si no hay ninguno, está creando uno. Eso no es lo que pretendías.
fuente
_
es simplemente incorrecto. Los identificadores que comienzan con dos guiones bajos (__example
) o los que comienzan con un guión bajo y una letra mayúscula (_Example
) están reservados._example
no está reservado.