保持サイクルを回避するために@ weakify @ strongifyを使用する必要があることは理解していますが、実際にこれをどのように達成するかを完全には理解していませんか?
質問を書くとき、私はマクロの定義をもっとじっと見つめました、そしてあなたが推測するかもしれないようにそれはうまくいくと思います。
@weakifyは、渡したのと同じタイプの弱く参照される新しい変数を作成し、元の値を割り当てます。
@strongifyは、元の変数と一致する変数を作成しますが、ローカルスコープに存在し、@ weakifyによって作成された変数を割り当てます。
前処理前のコード:
@weakify(self)
[[self.searchText.rac_textSignal
map:^id(NSString *text) {
return [UIColor yellowColor];
}]
subscribeNext:^(UIColor *color) {
@strongify(self)
self.searchText.backgroundColor = color;
}];
前処理後のコード:
@autoreleasepool {} __attribute__((objc_ownership(weak))) __typeof__(self) self_weak_ = (self);
[[self.searchText.rac_textSignal
map:^id(NSString *text) {
return [UIColor yellowColor];
}]
subscribeNext:^(UIColor *color) {
@try {} @finally {}
__attribute__((objc_ownership(strong))) __typeof__(self) self = self_weak_; // 1
self.searchText.backgroundColor = color; //2
}];
1:新しいローカル変数「self」を定義します。これはグローバルなものに影を落とします。
2:ここでは、ローカル変数「self」-self_weak_を使用しました。
チップ:
1.ブロックでself.xxxを使用した場合は、その上に@strongify(self)を配置する必要があります。
2. @weakify(self)を使用して変数self_weak_を定義することを忘れないでください。
(追記:私は英語を学ぼうとしています。私の言っていることが理解していただければ幸いです。)
何よりもまず、使用している@weakify
&@strongify
の実装は重要です。これらは、標準言語の一部ではないためです。 ReactiveCocoaバージョンを使用していると仮定すると、ここにニースがあります 記事 それらが何であるかとそれらがどのように機能するかについて。
ここにいくつかの関連する引用があります:
私たちが書いたコードnotでも、
self
を安全に使用できます。NSAssert
マクロ。self
を使用して、実際のivar
を参照することも可能です。ただし、警告が発生するため、簡単に見つけられる間違いです。さて、あなたは尋ねるかもしれません:もし私が
strongify
を使うのを忘れたらどうしますか?これはすばらしい部分です。weakify
は新しいローカル変数を作成するため、まったく使用されていない場合は警告が表示されます。ご想像のとおり、
weakify
の使用を忘れたが、その場所にstrongify
がある場合、コンパイラはエラーを表示します。