El número 1 se diferencia de los otros dos al declarar hacia adelante la clase MyOtherObject para minimizar la cantidad de código visto por el compilador y el enlazador y también potencialmente evitar referencias circulares. Si lo hace de esta manera, recuerde poner el #import en el archivo .m.
Al declarar un archivo @property (y hacer coincidir @synthesize en el .m), usted genera automáticamente métodos de acceso con la semántica de memoria manejada como usted lo especifica. La regla general para la mayoría de los objetos es Retain, pero NSStrings, por ejemplo, debería usar Copiar. Mientras que los Singletons y Delegates normalmente deberían usar Assign. Los accesos de escritura a mano son tediosos y propensos a errores, por lo que esto evita muchos errores de escritura y tontos.
Además, declarar una propiedad sintetizada le permite llamar a un método de acceso usando notación de puntos como esta:
self.otherObj = someOtherNewObject;
MyOtherObject *thingee = self.otherObj;
En lugar de la forma normal de pasar mensajes:
[self setOtherObject:someOtherNewObject];
MyOtherObject *thingee = [self otherObj];
Detrás de escena, realmente estás llamando a un método que se ve así:
- (void) setOtherObj:(MyOtherObject *)anOtherObject {
if (otherObject == anOtherObject) {
return;
}
MyOtherObject *oldOtherObject = otherObject;
otherObject = [anOtherObject retain];
[oldOtherObject release];
}
…o esto
- (MyOtherObject *) otherObject {
return otherObject;
}
Dolor total en el trasero, cierto. Ahora haz eso con cada ivar de la clase. Si no lo hace exactamente bien, obtendrá una pérdida de memoria. Es mejor dejar que el compilador haga el trabajo.
Veo que el Número 1 no tiene ivar. Suponiendo que no es un error tipográfico, está bien porque las directivas @property / @synthesize declararán un ivar para usted también, detrás de escena. Creo que esto es nuevo para Mac OS X: Snow Leopard e iOS4.
El número 3 no tiene esos accesos generados, por lo que debe escribirlos usted mismo. Si desea que sus métodos de acceso tengan efectos secundarios, haga su baile de administración de memoria estándar, como se muestra arriba, luego haga cualquier trabajo adicional que necesite, dentro del método de acceso. Si sintetiza una propiedad además de escribir la suya propia , entonces su versión tiene prioridad.
¿Cubrí todo?
setFoo:
yfoo
), puede usar la notación de puntos.En los viejos tiempos tenías ivars, y si querías dejar que otra clase los estableciera o los leyera, entonces tenías que definir un getter (es decir,
-(NSString *)foo)
y un setter (es decir,-(void)setFoo:(NSString *)aFoo;
).Lo que te dan las propiedades es el setter y getter gratis (¡casi!) Junto con un ivar. Entonces, cuando defina una propiedad ahora, puede establecer la atomicidad (¿desea permitir múltiples acciones de configuración de múltiples subprocesos, por ejemplo), así como asignar / retener / copiar semántica (es decir, si el establecedor copia el nuevo valor o simplemente guarde el valor actual - importante si otra clase está intentando establecer su propiedad de cadena con una cadena mutable que podría cambiarse más adelante).
Esto es lo que
@synthesize
hace. Muchas personas dejan el nombre de ivar igual, pero puede cambiarlo cuando escribe su declaración de síntesis (es decir,@synthesize foo=_foo;
significa hacer un ivar con el nombre_foo
de la propiedadfoo
, por lo que si desea leer o escribir esta propiedad y no la usaself.foo
, lo hará tiene que usar_foo = ...
, solo le ayuda a captar referencias directas al ivar si solo desea pasar por el setter y getter).A partir de Xcode 4.6, no es necesario utilizar la
@synthesize
declaración: el compilador lo hará automáticamente y, de forma predeterminada, antepondrá el nombre del ivar con_
.fuente