web-dev-qa-db-fra.com

Se référant au soi faible à l'intérieur d'un bloc imbriqué

Supposons que je crée déjà un moi faible en utilisant

__weak typeof(self) weakSelf = self;
[self doABlockOperation:^{
        ...
    }];

À l'intérieur de ce bloc, si j'imbrique un autre bloc:

[weakSelf doAnotherBlockOperation:^{
            [weakSelf doSomething];
}

créera-t-il un cycle de rétention? Dois-je créer une autre référence faible au soi faible?

__weak typeof(self) weakerSelf = weakSelf;
[weakSelf doAnotherBlockOperation:^{
                [weakerSelf doSomething];
    }
39
Enzo Tran

Ça dépend.

Vous ne créez un cycle de rétention que si vous stockez réellement le bloc (car self pointe vers le bloc et bloc pointe vers self). Si vous n'avez pas l'intention de stocker l'un des blocs, l'utilisation de la référence forte à self est suffisante --- le bloc sera libéré en premier après son exécution, puis il libérera son pointeur sur self.

Dans votre exemple particulier, sauf si vous effectuez plus d'opérations qui ne sont pas affichées, vous n'avez pas besoin de créer de weakerWeakerEvenWeakerSelfs.

19
George Karpenkov

Votre code fonctionnera correctement: la référence faible ne provoquera pas de cycle de rétention car vous demandez explicitement à ARC de ne pas augmenter le rétentionCompte de votre objet faible. Pour une meilleure pratique, cependant, vous devez créer une référence forte de votre objet en utilisant le faible. Cela ne créera pas non plus de cycle de rétention car le pointeur fort dans le bloc n'existera que jusqu'à la fin du bloc (sa seule portée est le bloc lui-même).

__weak typeof(self) weakSelf = self;
[self doABlockOperation:^{
    __strong typeof(weakSelf) strongSelf = weakSelf;
    if (strongSelf) {
        ...
    }
}];
60