2009-07-01 17 views
6

¿Estoy en lo cierto al suponer que añadir/eliminar elementos en un std :: map no afecta a los demás elementos (es decir, hacer que se reubiquen en la memoria) y que la siguiente es segura:C++ Almacenamiento de referencias a valores en std :: map

miré en varios sitios con información sobre el contenedor, pero sólo se enteraron de los casos en los que se han invalidado iteradores, que ya conozco ...

std::map<std::string,std::string> map; 
PopulateMap(map); 
std::string &a= map["x"]; 
AddMoreData(map); 
RemoveRandomKeysExceptX(map); 
map["x"] = "foo"; 
std::cout << a << " " << map["x"] << std::endl;//prints "foo foo" 
a = "bar"; 
std::cout << a << " " << map["x"] << std::endl;//prints "bar bar" 

que probé un poco de código similar sobre VC9 , lo que parece funcionar, sin embargo, eso no significa que no haya tenido suerte o que no varíe en los compiladores.

+0

No estoy seguro de por qué borró su respuesta nadeen, era correcta por lo que pude ver. – CiscoIPPhone

+0

La respuesta de naveen fue sobre iteradores, que esta pregunta no es –

+0

También borré mi respuesta, porque en la segunda lectura no tengo muy claro cuál es la pregunta real. –

Respuesta

8

El estándar es clara a este respecto en 23.1.2/8 acerca de los contenedores asociativos

Los miembros de inserción no afectará a la validez de los iteradores y las referencias al contenedor, y los miembros de borrado invalidará sólo iteradores y referencias a los elementos borrados.

+0

+1. Necesito tener a mano una copia del estándar. Mi respuesta podría haber sido más concisa y definitiva. – CiscoIPPhone

+0

Sí, siempre es una buena idea mantener abierta una instancia de okular/acroread para que pueda buscar cosas rápidamente =) En este caso, recordé la discusión que tuve aquí: http://stackoverflow.com/questions/516007/stdmap- puntero-a-mapa-clave-valor-es-esto-posible =) –

+0

Te animo a que voten la respuesta de @greg-rogers allí. Porque es el correcto, obviamente, mientras que la respuesta aceptada dice que no puedes estar seguro de esto. Pero el estándar es bastante claro, los indicadores siguen siendo válidos. –

3

El mapa tiene la importante propiedad de que insertar un nuevo elemento en un mapa no invalida los iteradores que apuntan a los elementos existentes. cita tomada de sgi docs.

Si se garantiza que los iteradores no cambian, los valores que señalan tampoco pueden cambiar.

naveen anteriormente tenía una respuesta que era similar a esto. A menos que haya un error en mi lógica, lo que estás haciendo es seguro.

Editar 2: Vea el punto 3 en sgi docs para ver cómo obtener un valor del operador [] es lo mismo que obtener el valor de un iterador.

+1

Como señalé a naveen (no nadeen) , la pregunta no es sobre iteradores. –

+0

Me doy cuenta de eso, pero el operador [] usa iteradores. – CiscoIPPhone

+0

Tenga en cuenta que los documentos de SGI tienen pequeñas discrepancias con la biblioteca estándar a veces, cuando se trata de detalles. –

0

Sí, puede contar con esto.

// retrieve reference to string stored at "x" 
// note that since [] returns a reference, it must insert an element at "x" if 
// it doesn't exists (in this case an empty string) 
std::string &a= map["x"]; 

// retrieve reference for "x" again and set value to "foo" 
map["x"] = "foo"; 

// use already stored reference 
a = "bar"; 
Cuestiones relacionadas