Todos los objetos utilizados como claves en NS (Mutable) Los diccionarios deben ser compatibles con el protocolo NSCopying, y esos objetos se copian cuando se usan en el diccionario.NSDictionary de Cocoa: ¿por qué se copian las claves?
Con frecuencia quiero usar objetos de mayor peso como claves, simplemente para asignar un objeto a otro. Lo que realmente quiero decir cuando hago eso es efectivamente:
[dictionary setObject:someObject forKey:[NSValue valueWithPointer:keyObject]];
("Cuando vuelva y te dará esta misma instancia de objeto tecla de nuevo, me consiguen el mismo valor a cabo.")
... que es exactamente lo que termino haciendo para evitar este diseño a veces. (Sí, sé de NSMapTable en Cocoa escritorio, pero por ejemplo, iPhone no soporta esta.)
Pero no lo que hago realmente entiendo es por qué copiando la clave es necesario o deseable en primer lugar. ¿Qué compra la implementación o la persona que llama?
Dirk: Gracias por esto. Creo que el hecho crítico que estaba malinterpretando (a lo que me llevó su respuesta) fue que la semántica de la clave es * no * sobre la referencia del objeto clave; se trata del contenido de la clave (de modo que la clave es la cadena "foo", ya sea de un literal, construido a partir de caracteres, lo que sea) - esto implica una comparación semántica, no un puntero. Pero las claves * deben * ser copiadas porque las claves mutables pueden cambiar. Donde esto me deja es que cuando realmente quiero usar un objeto para una clave, y realmente estoy detrás de la igualdad de referencia, mi enfoque no es un truco; es exactamente correcto –
Ben: No del todo. Si quiere '' keyObject' retenerse, ese código no lo hará, ya que trata 'keyObject' como un puntero a cualquier cosa, no necesariamente a un objeto, por lo que no tiene manera de saber que podría retenerlo. No estoy seguro de que 'value: withObjCType:' retenga, tampoco, si pasó '@encode (id)'. Para estar absolutamente seguro de que conserva sus llaves, necesitará usar NSMapTable (implica que no puede hacer esto porque está desarrollando para iPhone), use CFDictionary en lugar de NSDictionary (donde quiera que use el dict, no solo en su creación), o cree su propia subclase NSValue. –
Buen punto. Gracias por la información extra. Mientras lo pienso, nunca necesito claves para conservar cuando estoy usando este patrón. Por lo general, alguna otra colección en realidad "posee" los objetos que estoy usando como claves; Solo estoy usando el diccionario para asignarlos de manera eficiente a algún otro objeto relacionado. El peor de los casos es que el objeto clave se tramitaría, dejando una entrada turd en el diccionario. Lo único que tendría que tener cuidado es enumerar las claves reales y convertir los punteros en 'id's. Pero ese código huele lo suficientemente mal como para saber que estás haciendo algo peligroso ... –