0

私の問題はdispatch_async(dispatch_get_main_queue(), ^(void) { ... });、メソッドを非同期的に呼び出すために使用していることです。このメソッドでは、いくつかの条件に応じて、ブール値をに設定しYESます。このブール値がこのメソッドで読み取られると、常に古い値である。によって読み取られNOます。

奇妙なことに、ブール値がチェックされている行にブレークポイントを作成すると、すべてが正常に実行され、意図したとおりになりました。

編集:これはスレッドが生成されるコードです

dispatch_async(dispatch_get_main_queue(), ^(void) {
    [self drawFaceBoxesForFeatures:features forVideoBox:claporientation:curDeviceOrientation image:img];
});

メソッド自体

- (void)drawFaceBoxesForFeatures:(NSArray *)features forVideoBox:(CGRect)clap orientation:    (UIDeviceOrientation)orientation image:(UIImage *)image;
{
    if (![self getSendingRequestStatus]) {
        NSLog(@"Sending req");
        // send async request

         dispatch_async(dispatch_get_main_queue(),^ {
             sendingRequest = YES;
         } );
      }
}
4

2 に答える 2

3

ブロックの外側で作成された ivar をブロックの内側で変更しているようです。これを行い、ivar に正しい値を保持させるには、次の__blockようにキーワードを使用する必要があります。

@interface MyCoolClass : NSObject {
    @private
    __block int sendingRequest_;
}

ジャック・ローレンスが上記の称賛で述べたように、「[ランタイム] は、その時点で関連するすべてのオブジェクト/変数のスナップショットを取得します」。識別子は、その__blockivar をヒープにコピーしてはならないことをランタイムに伝え、sendingRequest_ブロックが単にメイン スレッドで実行されている場合でも、ブロック内に値を割り当てることができるようにします。

(上記を含む) 始めるのに役立つ多くの情報は、Blocks Programming Guideにあります。

于 2012-04-16T21:40:31.270 に答える
1

プリミティブがブロックに渡されると、それらがコピーされます。したがって、プリミティブローカル変数またはインスタンス変数をブロックに配置し、後でブロックを作成したのと同じメソッド(ブロックの作成後)または別のメソッドのいずれかで変更した場合、ブロック内の変数には影響しません。ローカル変数の場合は、ブロックを作成する前に必要な変更を加えてください。インスタンス変数の場合は、C:を使用してインスタンス変数にアクセスするかself->iVar、プロパティとして宣言し、プロパティアクセサー:を介してアクセスすることができますself.iVar

于 2012-04-16T21:23:27.013 に答える