wake-up-neo.com

Block behält implizit 'Selbst'; Erwähnen Sie ausdrücklich "Selbst", um anzuzeigen, dass dies beabsichtigtes Verhalten ist

Angesichts der folgenden:

- (void) someMethod
{
    dispatch_async(dispatch_get_main_queue(), ^{
        myTimer = [NSTimer scheduledTimerWithTimeInterval: 60
                                                           target: self
                                                         selector: @selector(doSomething)
                                                         userInfo: nil
                                                          repeats: NO];
    });
}

Wo myTimer in einer privaten Schnittstelle deklariert ist:

@interface MyClass()
{
    NSTimer * myTimer;
}
@end

Wie würde man die folgende Warnung beheben:

Block behält implizit 'Selbst'; Erwähnen Sie ausdrücklich "Selbst", um anzuzeigen, dass dies beabsichtigtes Verhalten ist

Nach dem, was ich bisher gefunden habe, beinhalten die meisten Vorschläge Folgendes:

- (void) someMethod
{
    __typeof__(self) __weak wself = self;
    dispatch_async(dispatch_get_main_queue(), ^{
        wself.myTimer = [NSTimer scheduledTimerWithTimeInterval: 60
                                                           target: self
                                                         selector: @selector(doSomething)
                                                         userInfo: nil
                                                          repeats: NO];
    });
}

Abgesehen davon, dass myTimer ein ivar ist, was bedeutet, dass wself keinen Zugriff auf Eigenschaften hat.

Ich denke meine Fragen sind:

  1. Interessiert mich/sollte es mich interessieren?
  2. Soll ich myTimer als Eigenschaft deklarieren?

Ich benutze Ivars ziemlich oft in meinem Code. Ich habe gerade das -Weverything Markieren Sie in meinem Projekt, ob ich zugrunde liegende Probleme finden kann. Dies ist bei weitem die häufigste Warnung. Ich habe zwar kein Problem damit, es zu beheben, indem ich meine ivars-Eigenschaften herstelle, aber ich möchte sicherstellen, dass ich ein besseres Verständnis habe, bevor ich das tue.

46
Kyle

Das Ersetzen von myTimer durch self->myTimer Würde Ihre Warnung beheben.

Wenn Sie eine iVar _iVar Im Code verwenden, ersetzt der Compiler den Code durch self->_iVar. Wenn Sie sie in einem Block verwenden, erfasst der Block sich selbst anstelle der iVar selbst. Die Warnung soll nur sicherstellen, dass der Entwickler dieses Verhalten versteht.

60
bsarr007

Einzelheiten

Xcode: 9.2, 10.2

Warnungen in Objective-C-Pods

Ich habe Swift Projekt. Warnung Block implicitly retains 'self'; explicitly mention 'self' to indicate this is intended behavior wird angezeigt, wenn ich Objective-C-Pods verwende:

  • Schrauben
  • FBSDKCoreKit
  • FBSDKLoginKit

enter image description here

Lösung 1 (manuell)

CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = NO

Lösung 2 (automatisch)

Fügen Sie am Ende Ihres Podfiles Folgendes hinzu:

post_install do |installer|
      installer.pods_project.targets.each do |target|
           target.build_configurations.each do |config|
                config.build_settings['CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF'] = 'NO'
           end
      end
 end

Ergebnisse

enter image description here

67

Für diejenigen unter Ihnen, die diese Warnungen aufgrund von Bolts/FBSDKCoreKit/FBSDKLoginKit erhalten, sollten Sie die Antwort von Vasily vermeiden und stattdessen die Warnungen für diese spezifischen Abhängigkeiten zum Schweigen bringen.

Option 1

Erwähne jeden Pod anstatt nur FacebookCore und füge inhibit_warnings: true Hinzu

pod 'FacebookCore', inhibit_warnings: true
pod 'Bolts', inhibit_warnings: true
pod 'FBSDKCoreKit', inhibit_warnings: true
pod 'FBSDKLoginKit', inhibit_warnings: true

Option 2

Oder bringen Sie alle Pods zum Schweigen, indem Sie Folgendes zu Ihrer Poddatei hinzufügen:

inhibit_all_warnings!

Fazit

Sie erhalten weiterhin Warnungen für Ihren eigenen Code. Irgendwann könnte es problematisch sein, diese nicht zu bekommen. Deshalb halte ich es für eine bessere Lösung.

Wenn Sie das nächste Mal die Facebook-SDK aktualisieren, prüfen Sie, ob Sie den inhibit_warnings: true Oder inhibit_all_warnings! Entfernen können.

15
Nycen

Dies behebt mein Problem für Xcode 9.3

- (void) someMethod{

    __weak MyClass *wSelf = self;

    dispatch_async(dispatch_get_main_queue(), ^{

    MyClass *sSelf = wSelf;
    if(sSelf != nil){
        wself.myTimer = [NSTimer scheduledTimerWithTimeInterval: 60
                                                       target: self
                                                     selector:@selector(doSomething)
                                                     userInfo: nil
                                                      repeats: NO];
       }

   });
}
3
Pooja Gupta

Vor kurzem stand ich vor dem gleichen Problem und die Antwort von @Vasily Bodnarchuk scheint hilfreich zu sein.

In Umgebungen mit kontinuierlicher Integration ist es jedoch nicht möglich, CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF Flag auf NO zur Laufzeit. Um das Problem einzugrenzen, habe ich versucht, alle von Cocoapods installierten abhängigen GEMS zu überprüfen und herauszufinden, dass die gem XCODEPROJ-Version 1.5.7 das CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF bis YES, wann immer pod install Befehl wird ausgeführt. Die Lösung dafür ist das Zurücksetzen der XCODEPROJ zu früherer Version 1.5.1 durch Ausführen von Sudo gem install xcodeproj -v 1.5.1 Einmal zurückgesetzt, einfach ausführen pod install und das Flag wird immer auf NO gesetzt.

2
bhuvan