¿Cómo verificar si std :: map contiene una clave sin insertar?


Respuestas:


305

Uso my_map.count( key ); solo puede devolver 0 o 1, que es esencialmente el resultado booleano que desea.

Alternativamente my_map.find( key ) != my_map.end()funciona también.


40
@John: Eso apesta a optimización prematura. En GCC (y estoy seguro de que los sistemas más razonables), map::countse implementa como find(__x) == end() ? 0 : 1;. Para multimapel puede tener un argumento de rendimiento, pero esa no es la pregunta de OP y todavía prefiero la elegancia.
— Potatoswatter

42
No, el argumento de optimización prematura solo es válido si la optimización requiere un esfuerzo que en este caso no es necesario.
— markh44

13
No es verdad. No es prematuro si hace que el código sea más fácil de leer o elimina la sobrecarga innecesaria. En este caso, si count () se implementa a través de find () de todos modos, entonces llamar a find () elimina directamente una función call ... ergo, es una optimización madura . Creo que usar la llamada find () también es más obvio, pero esa es una preferencia puramente personal.
— Tim Keating

9
No es una optimización prematura conocer el rendimiento de las funciones de la biblioteca antes de acostumbrarse a usarlas. En este caso, tiene razón, no importa, pero tampoco la minúscula diferencia estilística entre encontrar y contar. Creo que lleva demasiado lejos la retórica de la "optimización prematura". Debe tomar cualquier hábito de optimización "gratuito" que pueda encontrar y utilizarlo para el desarrollo diario. Es cuando los codificadores sucumben a la trampa de pagar costos en legibilidad / tiempo de desarrollo / etc., todo por "ganancias de rendimiento" no medidas que la retórica de optimización prematura se convierte en el consejo correcto para dar.
— VoidStar

10
Lejos, std solo debería agregar una maldita has(k)/ contains(k)como cualquier otra clase de mapa sensata en el planeta. Mal diseño de la interfaz. El enfoque find () es demasiado detallado y count(k)definitivamente no está en paridad semántica has(k). Para el caso tampoco lo es find(k). Mira el recuento de visitas en esta pregunta.
— Jarrod Smith

46

La respuesta de Potatoswatter está bien, pero prefiero usar findo en su lower_boundlugar. lower_boundes especialmente útil porque el iterador devuelto puede usarse posteriormente para una inserción insinuada, si desea insertar algo con la misma clave.

map<K, V>::iterator iter(my_map.lower_bound(key));
if (iter == my_map.end() || key < iter->first) {    // not found
    // ...
    my_map.insert(iter, make_pair(key, value));     // hinted insertion
} else {
    // ... use iter->second here
}

Esto es sutilmente diferente de cómo dice que lo está haciendo ... la única diferencia es que valuese puede omitir el cálculo si la inserción es innecesaria.
— Potatoswatter

1
Claro, entiendo que al OP no le importa insertar, por lo que una lower_boundsolución basada en es exagerada. Acabo de mencionar mi respuesta "para completar"; como dije, el tuyo es perfectamente adecuado. :-)
— Chris Jester-Young

44
Sí, esta es una buena respuesta y no estoy en desacuerdo con nada. Simplemente señalando la relación con la alternativa inserta priori. En realidad, hay otra diferencia si se usa a multimap, el lower_boundmétodo se inserta al comienzo del rango equivalente, mientras que el insertmétodo simple se agrega al final del rango.
— Potatoswatter

2
No es la respuesta a la pregunta, pero mi pregunta pobre me lleva a la respuesta correcta aquí ... Necesito hacer la inserción / actualización. : D
— Hunter-Orionnoir

1
@ Hunter ¿Puedes mostrarme tu código? Si no es masivo, probablemente pueda revisarlo por usted.
— Chris Jester-Young

Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.