gpt4 book ai didi

objective-c - iOS NSObject 在 block 中初始化后为零

转载 作者:行者123 更新时间:2023-12-03 16:58:11 26 4
gpt4 key购买 nike

我有一个在 block 内创建的 NSObject。按照下面的代码:

__block NSObject *myObject;

[self myMethod:^{
myObject = [[NSObject alloc] init];
....
}];

if(myObject == nil){
NSLog(@"Why is my object nil?!");
}

myMethod 的定义中,我有以下内容:

  backgroundQueue = dispatch_queue_create("backgroundqueue", NULL);

dispatch_async(backgroundQueue,
^{

dispatch_async(dispatch_get_main_queue(),
^{
if(block){
block();//Never called.
}
});

但是该 block 永远不会被调用。

最佳答案

这里的问题是,您似乎从未执行实例化 myObject 的 block 。为了便于说明,请运行这个小程序:

#import <Foundation/Foundation.h>

typedef void(^MyTestBlock)(void);

@interface Foo:NSObject
- (id)initWithBlock:(MyTestBlock)aBlock;
- (void)someMethod;
@end

@implementation Foo {
MyTestBlock _block;
}

- (id)initWithBlock:(MyTestBlock)aBlock {
self = [super init];
if( !self ) { return nil; }
_block = aBlock;
return self;
}

- (void)someMethod {
_block();
}

@end

int main(int argc, char *argv[]) {
@autoreleasepool {
__block NSObject *myObject;

Foo *myFoo = [[Foo alloc] initWithBlock:^{
myObject = [[NSObject alloc] init];
}];
[myFoo someMethod];

NSLog((myObject)?@"Your object was created":@"Why is my object nil?");
}
}

这会将 2012-11-26 05:00:58.519 Untitled 2[23467:707] Your object was Created 打印到控制台。关键是 block 不会自行执行。在上面的代码中,虽然我们将 block 设置为类的 ivar,但直到我们在 Foo 上调用 someMethod 时才会执行它。

编辑:

对您问题的编辑指出,该 block 不是在发送到主队列的异步调度 block 的上下文中执行的。如果这是命令行应用程序,则必须在 main 末尾调用 dispatch_main()。请参阅 dispatch_get_main_queue()man 页面。这是一个完整的工作命令行应用程序来说明这一点,以及与竞争条件相关的问题:

#import <Foundation/Foundation.h>

typedef void(^MyTestBlock)(void);

@interface Foo:NSObject
- (id)initWithBlock:(MyTestBlock)aBlock;
- (void)someMethod;
@end

@implementation Foo {
MyTestBlock _block;
}

- (id)initWithBlock:(MyTestBlock)aBlock {
self = [super init];
if( !self ) { return nil; }
_block = aBlock;
return self;
}

- (void)someMethod {
dispatch_queue_t backgroundQueue = dispatch_queue_create("backgroundqueue", NULL);
dispatch_async(backgroundQueue, ^{
dispatch_queue_t innerQueue = dispatch_get_main_queue();
dispatch_async(innerQueue, ^{
if( _block){
NSLog(@"Will call block.");
_block();
}
});
});

}

@end

int main(int argc, char *argv[]) {
@autoreleasepool {
__block NSObject *myObject;

Foo *myFoo = [[Foo alloc] initWithBlock:^{
myObject = [[NSObject alloc] init];
}];
[myFoo someMethod];

// this log statement should show that myObject is nil because it will (probably)
// be executed before your block.
NSLog((myObject)?@"Your object was created":@"Why is my object nil?");

// wait a little bit to resolve race condition (just for illustrative purposes)
dispatch_time_t popTime = dispatch_time(DISPATCH_TIME_NOW, 0.4f * NSEC_PER_SEC);
dispatch_after(popTime, dispatch_get_main_queue(), ^(void){
NSLog((myObject)?@"Your object was created":@"Why is my object nil?");
});
}
// this isn't a Cocoa app, so must call dispatch_main() at end of main
dispatch_main();
}

关于objective-c - iOS NSObject 在 block 中初始化后为零,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13563229/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com