Unterschied zwischen der @ Schnittstellendefinition in der .h- und .m-Datei

81

Normalerweise verwenden wir

@interface interface_name : parent_class <delegates>
{
......
}
@end 

Methode in der .h-Datei und in der .m-Datei synthetisieren wir die Eigenschaften der in der .h-Datei deklarierten Variablen.

In einigen Codes wird diese @interface ..... @ end-Methode jedoch auch in der .m-Datei gespeichert. Was heißt das? Was ist der Unterschied zwischen ihnen?

Geben Sie auch einige Wörter zu Gettern und Setzern für die Schnittstellendatei an, die in der .m-Datei definiert ist ...

Danke im Voraus

bgolson
quelle

Antworten:

63

Es ist üblich, eine zusätzliche zu setzen @interface Kategorie einzufügen, die eine Kategorie definiert, die private Methoden enthält:

Person.h:

@interface Person
{
    NSString *_name;
}

@property(readwrite, copy) NSString *name;
-(NSString*)makeSmallTalkWith:(Person*)person;
@end

Person.m:

@interface Person () //Not specifying a name for the category makes compiler checks that these methods are implemented.

-(void)startThinkOfWhatToHaveForDinner;
@end


@implementation Person

@synthesize name = _name;

-(NSString*)makeSmallTalkWith:(Person*)person
{
    [self startThinkOfWhatToHaveForDinner];
    return @"How's your day?";
}


-(void)startThinkOfWhatToHaveForDinner
{

}

@end

Die 'private Kategorie' (der richtige Name für eine namenlose Kategorie ist nicht 'private Kategorie', sondern 'Klassenerweiterung') .m verhindert, dass der Compiler warnt, dass die Methoden definiert sind. Da es sich bei der @interfacein der .m-Datei um eine Kategorie handelt, können Sie darin keine ivars definieren.

Update 6. August '12: Objective-C hat sich weiterentwickelt, seit diese Antwort geschrieben wurde:

  • ivars kann in einer Klassenerweiterung deklariert werden (und könnte es immer sein - die Antwort war falsch)
  • @synthesize ist nicht nötig
  • ivarskann jetzt in geschweiften Klammern oben angegeben werden @implementation:

das ist,

@implementation { 
     id _ivarInImplmentation;
}
//methods
@end
Benedict Cohen
quelle
4
Kleine Nebenbemerkung, setzen Sie eigentlich nichts in die Klammern, wenn Sie die private Schnittstelle deklarieren. Andernfalls wird nur eine Kategorie erstellt, und das möchten Sie nicht. @interface Person ()wird genügen.
Itai Ferber
Danke itaiferber, das hatte ich nicht bemerkt. Ich habe meine Antwort aktualisiert.
Benedict Cohen
4
Wenn Leute interessiert sind, mehr über Kategorien zu erfahren, war diese Seite für mich sehr nützlich.
Tim
1
Wenn nichts in den Klammern steht, wird dies tatsächlich als class extensionnicht acategory
Paul bezeichnet.
5
@ Riesen91 Diese Antwort ist ziemlich alt und der Compiler hat sich seit dem ersten Schreiben stark verbessert. Der Compiler benötigt keine Deklaration mehr für eine Methode, wenn der Methodenkörper 'sichtbar' ist. Dies bedeutet, dass Klassenfortsetzungen ( @interface className ()) im Allgemeinen nur private @propertys enthalten .
Benedict Cohen
10

Das Konzept ist, dass Sie Ihr Projekt viel sauberer machen können, wenn Sie die .h-Datei auf die öffentlichen Schnittstellen Ihrer Klasse beschränken und dann Details zur privaten Implementierung in diese Klassenerweiterung einfügen.

Wenn Sie Variablenmethoden oder -eigenschaften in der Datei ABC.h deklarieren, bedeutet dies, dass auf diese Variableneigenschaften und -methoden außerhalb der Klasse zugegriffen werden kann

@interface Jain:NSObject
{
    NSString *_name;
}

@property(readwrite, copy) NSString *name;
-(NSString*)makeSmallTalkWith:(Person*)jain;
@end

Mit @Interface können Sie private Ivars, Eigenschaften und Methoden deklarieren. Auf alles, was Sie hier deklarieren, kann also nicht von außerhalb dieser Klasse zugegriffen werden. Im Allgemeinen möchten Sie alle ivars, Eigenschaften und Methoden standardmäßig als privat deklarieren

Sagen Sie einfach, wenn Sie Variablenmethoden oder -eigenschaften in der ABC.m-Datei deklarieren. Dies bedeutet, dass auf diese Variableneigenschaften und -methoden außerhalb der Klasse nicht zugegriffen werden kann

@interface Jain()
    {
        NSString *_name;
    }

    @property(readwrite, copy) NSString *name;
    -(NSString*)makeSmallTalkWith:(Person*)jain;
    @end
Shubham JAin
quelle
0

Sie können sogar andere Klassen in der .m-Datei erstellen, z. B. andere kleine Klassen, die von der in der .h-Datei deklarierten Klasse erben, jedoch ein geringfügig anderes Verhalten aufweisen. Sie können dies in einem Fabrikmuster verwenden

Enrico Cupellini
quelle