2009-05-27 27 views
9

Soy nuevo en el objetivo C y solo quería obtener una aclaración general sobre cuándo usar un puntero y cuándo no, al declarar las variables de instancia.Punteros de variable de instancia Objective-C

El ejemplo en el que puedo pensar es UIView vs. a BOOL. UIView Haría un puntero, BOOL no lo haría (porque el compilador me gritó).

Cualquier orientación general sería increíble.

Saludos,

Respuesta

20

Si se trata de un objeto, que utilizan la notación de puntero. Todos los tipos de c (int, BOOL, largo, etc.) no son objetos y por lo tanto sólo utiliza un puntero si quieres un puntero a su ubicación en la memoria:

NSObject *obj; 
UIView<Protocol> *obj; 
int integerVar; 
BOOL isTrue; 

Un caso especial es id, que es en sí misma un puntero a un objeto, por lo que no es necesario el *:

id obj; 

poco complicado:

NSInteger int; 
NSNumber *number; 

NSInteger es el int dad específica de la plataforma adecuada pe, mientras que NSNumber es un objeto que puede contener un int, float o lo que sea.

+2

Gracias por su respuesta. Esto me deja preguntando ahora, ¿cómo se limpian los tipos C de la memoria? ¿Se hace bajo el capó Objective-C? – Meroon

+1

Las variables de instancia del objeto están todas contenidas dentro de la memoria del objeto. Todos desaparecerán cuando se libere la memoria del objeto. La diferencia con las variables de tipo objeto es que son punteros, lo que significa que la variable en sí misma apunta a un lugar en la memoria. Incluso si la variable del puntero desaparece, la memoria a la que apunta sigue asignada. – Chuck

+2

No olvide que algunas veces en los archivos de cabecera, Apple ha configurado typedefs para estructuras donde siempre se refiere a ellas con un puntero. En ese caso, el nombre termina en "Ref". p.ej. CGImageRef que es un typedef de CGImage *. Cuando vea que no coloca su propio * en el nombre de la variable. – U62

5

Los apuntadores se utilizan para mantener la dirección de la memoria asignada. Cuando crea un objeto en cocoa, asigna memoria y almacena la dirección en puntero.

BOOL, char, int almacenar el valor.

Cuando se crea una clase del alloc asigna memoria por lo que necesita para almacenar un puntero a la memoria para poder acceder a ella:

NSMutableArray * arr = [[NSMutableArray alloc] init]; 

¿Cómo los tipos C se limpiaron de la memoria?

Los tipos "simples" se asignan en la pila. Cuando se llama a un método, se asigna un espacio en la pila para contener todas las variables de método (más algunas otras cosas como parámetros y dirección de retorno, etc.). Entonces la pila crece Una vez que el método retorna, la pila se reduce y el espacio que utilizó el método ahora se reclama, así que sí, los tipos simples se "limpiarán".

En realidad es mucho más simple de lo que parece. Eche un vistazo a wikipedia Stack entry - section Hardware stacks para más detalles para satisfacer su curiosidad.

Cuando "asigna memoria" esa memoria se asigna en el montón. Heap está ahí para la ejecución completa de su aplicación. Una vez que asigna la memoria en un montón, obtiene una dirección para esa memoria: almacena esta dirección en punteros. Puntero es solo una variable que almacena la dirección de memoria.

Cuando su método retorna ya no tiene acceso a sus variables 'simples' declaradas dentro del método (por ejemplo, BOOL, int, char, etc.) pero la memoria en el montón todavía está allí. Si aún tiene la dirección de la memoria (por ejemplo, el puntero), puede acceder a ella.

¿Qué pasa con las variables de instancia de tipo 'simple' (editar: ¿objeto interior?)?

Cuando crea un objeto (estamos hablando de objetivo C y Cocoa aquí) y le asigna espacio para todo el objeto.El tamaño del objeto es el tamaño de todas sus variables (no estoy seguro de si obj-c agrega otras cosas). Entonces, las variables de instancia son parte de la memoria de objeto en Heap. Cuando sueltas/borras objetos su memoria es recuperada y ya no tienes acceso a las variables que están almacenadas dentro del objeto (en obj-c llamas liberación, cada objeto guarda conteo de referencias, cuando el recuento de referencias llega a 0 el objeto es desasignado - el la memoria en el montón es recuperada).

+0

Oh ok que enmascara el sentido de las variables locales dentro del alcance del método. Pero, ¿qué pasa con las variables de instancia que son tipos "simples"? – Meroon

1

Cada clase de Objective-C, como NSString, NSObject, NSView, etc. debe ser un puntero, a excepción de algunos tipos especiales como NSUInteger, que es solo un typedef para int creo.

NSString *stringyString = @"THIS STRING IS STRINGY!!!11"; 
NSOpenPanel *openPanel; 
NSObject *objectyObject; 
NSUInteger integeryInteger = 7; 

Lo único que no se identificará es que es un puntero a cualquier objeto.

id pointerThatCanBeSetToAnyObject = [NSString stringWithString:@"HEYYYY"]; 

Sólo C tipos de variables como int, float, BOOL, etc., no requerirán un puntero, a excepción de cadenas de C como arrays de char.

int SEVEN = 7; 
float SIXPOINTTWO = 6.2; 
char *characterArray = "HEYYYYY"; 

Finalmente, las clases de CoreFoundation tienen una especie de híbrido; muchas clases serán punteros, pero para algunas clases, como CFString, un CFStringRef ya será un puntero. Muchas funciones de CFString regresan como CFStringRef. CFString * y CFStringRef son intercambiables con NSString * (esto se conoce como puente libre de costo), aunque el compilador probablemente lo aprecie si lo lanza primero.

CFString *veryStringyString = @"STRINGYNESS!!11!one"; 
CFStringRef especiallyStringyString = @"STRRRRRRINNNNNGGGGYYYYY"; 
NSString *STRINGYNESS = (NSString *)veryStringyString; 
Cuestiones relacionadas