我有一个 dispatch_block_t
被传递给另一个函数,这个 block 将在函数时被调用> 完成异步任务。但问题是我不知道这个 block 将调用哪个线程。
我想在主线程中更新我的用户界面,因此我想使用
dispatch_async(dispatch_get_main_queue(), ^{...})
更新我的用户界面。但如果发生这种情况,恐怕会导致死锁
dispatch_queue_t queue = dispatch_queue_create("my.label", DISPATCH_QUEUE_SERIAL);
dispatch_async(queue, ^{
dispatch_async(queue, ^{
// outer block is waiting for this inner block to complete,
// inner block won't start before outer block finishes
// => deadlock
});
// this will never be reached
});
有没有办法防止死锁?就像在不使用 dispatch queue
的情况下更新 UI 元素一样。是否可以创建对 self
的弱引用
以更新 UI?
最佳答案
尝试使用 NSLogs 运行您的示例,您会发现死锁不会发生。这是因为使用 dispatch_async
只是将一个 block 提交到队列而不等待它完成执行(与 dispatch_sync
相反)。
所以运行这段代码:
dispatch_queue_t queue = dispatch_queue_create("my.label", DISPATCH_QUEUE_SERIAL);
dispatch_async(queue, ^{
NSLog(@"1");
dispatch_async(queue, ^{
NSLog(@"2");
});
NSLog(@"3");
});
将产生以下日志:
Testtt[32153:2250572] 1
Testtt[32153:2250572] 3
Testtt[32153:2250572] 2
此外,我担心这里使用 dispatch_async(dispatch_get_main_queue(), ^{...})
是确保消费者在主线程上获得结果的常用技术(即消费者不“关心”线程)。
为什么要使用 dispatch_block_t
来传递完成 block ?在我看来,在消费者端使用类似的东西有点令人困惑——我会传递一个匿名(没有 typedef) block 或为这些简单的完成 block 创建我自己的 typedef。
关于ios - 在不分派(dispatch)到主队列的情况下更新 UI 元素,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/51991011/