Me preguntaba cómo suprimir la advertencia:
Category está implementando un método que también será implementado por su clase primaria.
Tengo esto para una categoría de código específica:
+ (UIFont *)systemFontOfSize:(CGFloat)fontSize {
return [self aCustomFontOfSize:fontSize];
}
objective-c
clang
Doz
fuente
fuente
super
otra manera.Respuestas:
Una categoría le permite agregar nuevos métodos a una clase existente. Si desea volver a implementar un método que ya existe en la clase, normalmente crea una subclase en lugar de una categoría.
Documentación de Apple: personalización de clases existentes
Dos métodos con exactamente la misma firma en la misma clase darían lugar a un comportamiento impredecible, porque cada llamador no puede especificar qué implementación desea.
Por lo tanto, debe usar una categoría y proporcionar nombres de método que sean nuevos y únicos para la clase o subclase si desea cambiar el comportamiento de un método existente en una clase.
fuente
Aunque todo lo que se ha dicho correctamente es correcto, en realidad no responde a su pregunta de cómo suprimir la advertencia.
Si tiene que tener este código por alguna razón (en mi caso, tengo HockeyKit en mi proyecto y anulan un método en una categoría UIImage [editar: este ya no es el caso]) y necesita que su proyecto se compile , puede usar
#pragma
declaraciones para bloquear la advertencia de la siguiente manera:Encontré la información aquí: http://www.cocoabuilder.com/archive/xcode/313767-disable-warning-for-override-in-category.html
fuente
Una mejor alternativa (vea la respuesta de bneely a por qué esta advertencia lo está salvando de un desastre) es usar el método swizzling. Al utilizar la combinación de métodos, puede reemplazar un método existente de una categoría sin la incertidumbre de quién "gana", y al mismo tiempo conservando la capacidad de llamar al método anterior. El secreto es darle a la anulación un nombre de método diferente y luego intercambiarlos usando funciones de tiempo de ejecución.
Luego defina su implementación personalizada:
Anula la implementación predeterminada con la tuya:
fuente
Prueba esto en tu código:
ACTUALIZACIÓN2: agregue esta macro
fuente
Puede utilizar el método swizzling para suprimir esta advertencia del compilador. Así es como implementé el método swizzling para dibujar márgenes en un UITextField cuando usamos un fondo personalizado con UITextBorderStyleNone:
fuente
Las propiedades primarias son válidas para una extensión de clase (categoría anónima), pero no para una categoría normal.
Según Apple Docs, utilizando una extensión de clase (categoría anónima), puede crear una interfaz privada para una clase pública, de modo que la interfaz privada pueda anular las propiedades expuestas públicamente. es decir, puede cambiar una propiedad de readonly a readwrite.
Un caso de uso para esto es cuando escribe bibliotecas que restringen el acceso a propiedades públicas, mientras que la misma propiedad necesita acceso completo de lectura y escritura dentro de la biblioteca.
Enlace de Apple Docs: https://developer.apple.com/library/ios/documentation/Cocoa/Conceptual/ProgrammingWithObjectiveC/CustomizingExistingClasses/CustomizingExistingClasses.html
Busque " Usar extensiones de clase para ocultar información privada ".
Entonces, esta técnica es válida para una Extensión de clase, pero no para una Categoría.
fuente
Las categorías son algo bueno, pero se puede abusar de ellas. Al escribir categorías, como principio, NO debe volver a implementar los métodos existentes. Si lo hace, puede causar un efecto secundario extraño, ya que ahora está reescribiendo el código de que otra clase depende de una. podría romper una clase conocida y terminar volviendo su depurador al revés. Es simplemente una mala programación.
Si necesita hacerlo, debería subclasificarlo.
Entonces la sugerencia de swizzling, eso es un gran NO-NO-NO para mí.
Pasarlo en tiempo de ejecución es un NO-NO-NO completo.
¿Quieres que un plátano se vea como una naranja, pero solo en tiempo de ejecución? Si quieres una naranja, escribe una naranja.
No hagas que un plátano se vea y actúes como una naranja. Y lo que es peor: no conviertas tu plátano en un agente secreto que saboteará silenciosamente los plátanos en todo el mundo en apoyo de las naranjas.
¡Ay!
fuente
Tuve este problema cuando implementé un método delegado en una categoría en lugar de la clase principal (aunque no había una implementación de clase principal). La solución para mí fue mover del archivo de encabezado de clase principal al archivo de encabezado de categoría Esto funciona bien
fuente