2010-11-04 10 views
15

¿Es posible definir sus propios operadores de ruta clave, tales como @avg, @Sum, etc ...La definición de sus propios operadores de ruta clave en el cacao

+2

Tengo que seguir luchando contra la necesidad de enviar preguntas sobre el cacao al sitio de cocina ... –

+2

+1 esta es una pregunta realmente fascinante; uno que nunca pensé preguntar, pero que ha revelado información realmente interesante. ¡Gracias por preguntar! –

Respuesta

14

Respuesta corta: Un poco. Puede anular valueForKeyPath: para interceptar su operador personalizado o reenviar a super, pero eso puede ser problemático (dejaré la explicación como un ejercicio para el lector).

Respuesta larga: Sí, puede, pero se basa en el uso de comportamiento privado (no api privado).

Después de un poco de introspección ordenada de NSArray, he encontrado algunos métodos particulares:

_distinctUnionOfSetsForKeyPath: 
_distinctUnionOfObjectsForKeyPath: 
_distinctUnionOfArraysForKeyPath: 
_unionOfSetsForKeyPath: 
_unionOfArraysForKeyPath: 
_unionOfObjectsForKeyPath: 
_minForKeyPath: 
_maxForKeyPath: 
_countForKeyPath: 
_avgForKeyPath: 
_sumForKeyPath: 

Bueno, limpio! Esos métodos parecen coincidir con los operadores que puede usar con colecciones: @sum, @min, @max, @distinctUnionOfObjects, etc. El @ ha sido reemplazado con un guión bajo y tenemos ForKeyPath: adjunto.

Parece que podemos crear un nuevo método para que coincida con la firma adecuada y estamos listos para continuar.

Así:

@interface NSArray (CustomOperator) 

- (id) _fooForKeyPath:(NSString *)keyPath; 

@end 

@implementation NSArray (CustomOperator) 

- (id) _fooForKeyPath:(NSString *)keyPath { 
    //keyPath will be what comes after the keyPath. In this example, it will be "self" 
    return @"Hello world!"; 
} 

@end 

NSArray * array = [NSArray arrayWithObjects:@"1", @"2", @"3", nil]; 
NSLog(@"%@", [array valueForKeyPath:@"@foo.SELF"]); //logs "Hello world!" 

Funciona, pero no estoy seguro de que confiar en esto, ya que depende de un detalle de implementación que podría cambiar en el futuro.

+2

Ignorar '-valueForKey:' en lugar de eso, lo haría. Lea los documentos sobre cómo NSDictionary lo implementa. –

+1

@Mike a largo plazo es probablemente más estable, pero el problema con la anulación es que estos operadores generalmente solo son útiles en colecciones, y la subclasificación de colecciones es una mierda. :( –

+1

Nice find Dave! Sin embargo, parece un bi frágil como dijiste. ¿Por qué crees que el valor superior ForKeyPath: es más peligroso? – cfischer

0

Es posible reemplazando valueForKeyPath: y haciendo su propia lógica personalizada allí, pero no hay soporte de marco para eso.

Cuestiones relacionadas