2010-12-30 26 views
1

Wir deklarieren Eigenschaften mit dem Schlüsselwort @property und synthetisieren es in der Implementierungsdatei. Meine Frage istWas ist der beste Weg, um eine Eigenschaft zu deklarieren?

Was passiert, wenn ich eine Eigenschaft mit dem Schlüsselwort @property deklariere und auch eine Variable im gleichnamigen Interface-Block deklariere? Betrachten wir zum Beispiel den folgenden Code,

Schnittstelle:

@interface myClass : NSObject { 

    NSString *myClass_name; // LINE 1 
} 

@property(nonatomic, retain) NSString *myClass_name; // LINE 2 

@end 

Umsetzung:

@implementation myClass 

@synthesize myClass_name // LINE 3 

@end 

Deklarieren myClass_name in LINE 1 wird jedes Problem machen? Wie jedes Referenzproblem oder jedes unnötige Speicherverbrauchsproblem?

Antwort

3

Nein, tatsächlich deklariert Eigenschaften wie das erwartet es. Sie könnten Ihre Erklärung ersetzen:

@interface MyClass : NSObject { 
    NSString *ivar; 
} 

@property (nonatomic, retain) NSString *myClass_name; 

@end 

Und dann Ihre Implementierung

@implementation MyClass 

@synthesize myClass_name = ivar; 

@end 

ändern (Wenn Sie die = some_ivar angeben, wird annehmen, dass es die Ivar den gleichen Namen wie die Eigenschaft hat, .)

Sie müssen immer die folgenden Zeilen haben:

  • Erklärung der Eigenschaft (Linie 2)
  • Synthetisierung der Immobilie (Linie 3)

Wenn Sie die Eigenschaft synthetisieren, wenn Sie nicht angeben, die (durch =ivar am Ende mit) verwenden Ivar wird es annehmen, dass es ein Ivar ist mit derselbe Name wie die Eigenschaft.

+1

In diesem Fall brauche ich nicht LINE 2? – EmptyStack

+0

@Simon Korrigieren. –

+0

@Justin Spahr-Summers: Ich brauche die LINE 2 oder nicht? Ich weiß es wirklich nicht. Bitte sag es mir. – EmptyStack

1

Wenn Sie Eigenschaften deklarieren und synthetisieren, wird in Ihrem Fall kein Referenzproblem erzeugt. Dadurch werden Accessor- und Setter-Methoden für Ihre Instanzvariable in Ihrer Klasse erstellt. Wenn die Variablennamen in der Eigenschaft und in der Klasse deklariert sind, bezieht sich der xcode auf beide als einzelne Variable.

Zeile 3 und Zeile 4 sind Muss. Zeile 1 ist optional

+0

Welche Linie meinen Sie mit Linie 4? – EmptyStack

+0

LINE 1 ist in meinem Code erforderlich? – EmptyStack

+0

oh sorry mein Fehler, ich meinte Linie 2 und Linie 3 sind müssen. Außerdem habe ich versucht, Zeile 1 wegzulassen und den Code auszuführen. Tritt in Ihrem Fall ein Fehler auf, wenn Sie Zeile 1 auslassen? – Snehal

1

Ich habe den folgenden Inhalt von Apples Dokument für Declared Properties erhalten. Ich poste es hier, damit es für jemanden in Zukunft hilfreich sein kann.

Runtime Difference

Im Allgemeinen das Verhalten von Eigenschaften ist identisch auf allen Laufzeiten (siehe Runtime Versions and Platforms in Objective-C Runtime Programming Guide). Es gibt einen entscheidenden Unterschied: Die moderne Laufzeitumgebung unterstützt die Synthese der Instanzvariablen, während die Legacy-Laufzeitumgebung dies nicht unterstützt.

Für @synthesize in der alten Laufzeit zu arbeiten, müssen Sie eine Instanzvariable mit dem gleichen Namen und kompatiblen Typ der Eigenschaft entweder liefern oder eine andere vorhandene Instanz Variable in der @synthesize Anweisung angeben. Wenn Sie bei der modernen Laufzeit keine Instanzvariable bereitstellen, fügt der Compiler eine Instanz hinzu.Um zum Beispiel die folgende Klassendeklaration und Umsetzung gegeben:

@interface MyClass : NSObject { 

    float sameName; 
    float otherName; 
} 

@property float sameName; 
@property float differentName; 
@property float noDeclaredIvar; 

@end 


@implementation MyClass 

@synthesize sameName; 
@synthesize differentName=otherName; 
@synthesize noDeclaredIvar; 

@end 

der Compiler für die Legacy-Laufzeit würde einen Fehler bei @synthesize noDeclaredIvar; während der Compiler für die moderne Laufzeit erzeugen würde eine Instanzvariable hinzufügen noDeclaredIvar darzustellen.

1

Das Folgende ist die objektorientierte Art und Weise:

DeclaringProperties.h

@interface DeclaringProperties : NSObject 
// ivars and {} can be omitted 

@property (nonatomic, readwrite, retain) NSString *normal; 
@property (nonatomic, readwrite, retain) NSString *alias; 
@property (nonatomic, readonly, retain) NSString *readonly; 

- (id) initWithNormal:(NSString *)aNormal alias:(NSString *)alias; 

@end 

DeclaringProperties.m

#import "DeclaringProperties.h" 

// private interface 
@interface DeclaringProperties() 

@property (nonatomic, readwrite, retain) NSString *readonly; // readwrite for self 
@property (nonatomic, readwrite, retain) NSString *private; 
@property (nonatomic, readwrite, retain) NSString *retain; 

@end 

#pragma mark - 

@implementation DeclaringProperties 

@synthesize normal, alias = _alias, readonly, private, retain; 

// You can not use "normal" here; 
// But you can still use "alias", and it is highlighted in XCode! 
- (id) initWithNormal:(NSString *)aNormal alias:(NSString *)alias { 
    self = [super init]; 
    if (self) { 
     self.normal = aNormal; 
     self.alias = alias; 
     self.readonly = @"readonly"; 
     self.private = @"private"; 

     // allocated(copied) variable for retained(copied) property should be released or autoreleased 
     NSString *alloc = [[NSString alloc] init]; 
     self.retain = alloc; 
     [alloc release]; 
     // or 
     self.retain = [[NSString alloc] init]; 
     [self.retain release]; 
     // or 
     self.retain = [[[NSString alloc] init] autorelease]; 
     // I don't like ;) 
     retain = [[NSString alloc] init]; 
    } 
    return self; 
} 

- (void) dealloc { 
    self.normal = nil; 
    self.alias = nil; 
    self.readonly = nil; 
    self.private = nil; 
    self.retain = nil; 
    [super dealloc]; 
} 

@end 
Verwandte Themen