2013-09-02 10 views
31

Ich versuche, meine App mit Xcode5 zu aktualisieren, stieß aber auf eine Reihe von "semantischen Problemen" in einer Third-Party-Bibliothek (MagicalRecord). Der schnellste Weg zur ‚fix‘ könnte dies unter Verwendung der:Sollte ich Xcode 5 'Semantisches Problem: nicht deklarierter Selektor' beheben?

#pragma GCC diagnostic ignored "-Wundeclared-selector" 

(aus: How to get rid of the 'undeclared selector' warning)

Compiler-Direktive, aber mein Bauchgefühl sagt, dass dies nicht der richtige Weg, dies zu tun. Ein kleines Codebeispiel mit dem obigen Fehler:

+ (NSEntityDescription *) MR_entityDescriptionInContext:(NSManagedObjectContext *)context { 

    if ([self respondsToSelector:@selector(entityInManagedObjectContext:)]) 
    { 
     NSEntityDescription *entity = [self performSelector:@selector(entityInManagedObjectContext:) withObject:context]; 
     return entity; 
    } 
    else 
    { 
     NSString *entityName = [self MR_entityName]; 
     return [NSEntityDescription entityForName:entityName inManagedObjectContext:context]; 
    } 
} 

wo die entityInManagedObjectContext: Methode nicht überall definiert ist.

Haben Sie Vorschläge, wie Sie diese Fehler am besten beheben können? Vielen Dank im Voraus ?!

Antwort

20

Sie brauchen nur eine Klasse oder ein Protokoll zu erklären, dass der Selektor enthält. Zum Beispiel:

// DeliveryTimeComparison.h 
#import <Foundation/Foundation.h> 

@protocol DeliveryTimeComparison <NSObject> 

- (void)compareByDeliveryTime:(id)otherTime; 

@end 

Und dann einfach #import "DeliveryTimeComparison.h" in jeder Klasse, wo Sie planen @selector(compareByDeliveryTime:) zu verwenden.

Oder importieren Sie einfach den Klassenheader für jedes Objekt, das eine Methode "compareByDeliveryTime:" enthält.

+0

Ich stimme der obigen Methode zu, da das Deaktivieren von Warnungen nicht meine bevorzugte Methode zum' Reparieren 'ist. Mit der entsprechenden Header-Datei und den Klassen-/Protokollnamen kann ich diese dokumentierte "Schnellkorrektur" einfacher finden. Also denke ich, dass ich Abhis Methode übernehmen werde. –

+1

Das klingt gut, es sei denn, Sie können die Klasse, in der der Selektor sein sollte, nicht wirklich einbeziehen/importieren (Zyklusabhängigkeitsprobleme, ..) – Gyfis

15

Xcode 5 hat diese Option standardmäßig aktiviert. Um es auszuschalten, gehen Sie auf "Build Settings" für Ihr Ziel unter "Apple LLVM 5.0 - Warnungen - Objective C" -> "Undeclared Selector" auf "NO". Dies sollte dafür sorgen.

+6

dies die Frage zu beantworten, tut zu umgeben, wie die Warnung zu beheben, anstatt die Warnung verhindert von Happening .. -1 dafür! –

+7

Einverstanden. Aber für diejenigen unter uns, die größere Probleme mit iOS 7 lösen wollen, können Sie diese ausblenden, bis Sie zu einem späteren Zeitpunkt mit ihnen fertig werden. Und Sie werden keine Probleme haben, Apps mit diesen Warnungen zu senden. –

25

Ja, Sie sollten.

statt, dies zu tun:

[self.searchResults sortUsingSelector:@selector(compareByDeliveryTime:)]; 

Sie sollten dies tun:

SEL compareByDeliveryTimeSelector = sel_registerName("compareByDeliveryTime:"); 
[self.searchResults sortUsingSelector:compareByDeliveryTimeSelector]; 
+0

Danke. Dies hat auch eine Warnung "Die App verweist nicht öffentliche Selektoren in Payload" beseitigt, die ich während des Einreichprozesses erhalten habe. Nachdem ich den Selektor wie oben beschrieben deklariert hatte, konnte ich die App ohne Warnungen einreichen. –

+8

Irgendwelche Idee * warum * war die Standard-Build-Einstellung? Was kostet Sie den Aufruf von sel_registerName (also explizit 'Registrieren einer Methode mit der Objective-C-Laufzeit') (abgesehen von der zusätzlichen Zeile)? – Blaz

+2

Es scheint mir, dass dies die Warnung * nicht * repariert *, es versteckt es einfach.Um es richtig zu beheben, sollte die Datei eingeschlossen werden, in der der Selektor deklariert wurde, da dann, wenn dieser Selektor aus irgendeinem Grund umbenannt wird, die Warnung wieder erscheint, was wir uns wünschen. – Brane

10

Diese Auswahlwarnungen in MagicalRecord dienen der Kompatibilität mit generierten Core Data-Klassen. Abgesehen von der Verwendung von Mogenerator und vielleicht dem Import einer der Entitäten gibt es wirklich nicht viel, was Sie tun können außer dem, was bereits beantwortet wurde.

Eine andere Möglichkeit ist natürlich, dass Code speziell mit ignorieren Blöcke

#pragma clang diagnostic push 
#pragma clang diagnostic ignored "-Wundeclared-selector" 

und am Ende

#pragma clang diagnostic pop