我是iPhone开发的新手,并且通过GCD概念进行多线程处理。
' dispatch_queue_t'创建一个串行队列,我已经读过一个串行队列一次只能执行一个作业。 GCD旨在同时执行多个任务,然后为什么串行队列存在?
例如,我想做2个任务。任务A和任务B.我创建一个串行队列来执行这两个任务。我在主队列中这样做。这是我正在做的代码:
dispatch_queue_t my_serial_queue = dispatch_queue_create("queue_identifier", 0);
dispatch_sync(my_serial_queue, ^{
NSLog(@"Task 1");
});
dispatch_sync(my_serial_queue, ^{
NSLog(@"Task 2");
});
现在,根据规则,任务都将串行执行,因为它是串行队列,即首先执行任务A,然后在任务A完成后执行任务B.而且它在日志中给我相同的输出。
所以,我的问题是,如果我想同时执行这两项任务怎么办?如果这个问题的答案是为任务B创建另一个串行队列,那么代码的结构应该是这样的:
dispatch_queue_t my_serial_queue_1 = dispatch_queue_create("queue_identifier_1", 0);
dispatch_queue_t my_serial_queue_2 = dispatch_queue_create("queue_identifier_2", 0);
dispatch_sync(my_serial_queue_1, ^{
NSLog(@"Task 1");
});
dispatch_sync(my_serial_queue_2, ^{
NSLog(@"Task 2");
});
我得到相同的输出。原因是我正在使用' dispatch_sync'打电话代替' dispatch_async'呼叫。但是当我在不同的队列中运行这两个任务时,它们不应该同时执行吗?如果没有,那么我们为什么要创建一个不同的队列呢?我可能通过' dispatch_async'使用相同的队列。要求同时执行这两项任务。
我真的需要回答这个问题,因为在将来设计我的多任务应用程序的结构之前,它会更好地指导我。
答案 0 :(得分:5)
您的困惑几乎完全是因为您正在使用dispatch_sync。 dispatch_sync 不是用于获取并发执行的工具,它是暂时限制安全性的工具。
一旦使用了dispatch_async,就可以通过拥有多个队列或使用并发队列来获得并发。在此上下文中使用串行队列的目的是控制同时完成哪些工作。
考虑以下非常愚蠢的例子:
__block void *shared = NULL;
for (;;) {
dispatch_async(aConcurrentDispatchQueue, ^{
shared = malloc(128);
free(shared);
}
}
这会崩溃,因为最终,两个并发执行的块将连续释放'共享'。这显然是一个人为的例子,但在实践中,几乎所有共享的可变状态都不能同时更改。串行队列是确保您这样做的工具。
汇总:
答案 1 :(得分:1)
' dispatch_queue_t'没有创造任何东西。 dispatch_queue_t 是调度队列,可以是串行队列,也可以是并发队列。
dispatch_queue_create有两个参数。第二个参数决定它创建的队列是串行队列还是并发队列。但通常您不会自己创建并发队列,而是使用三个现有并发队列中的一个。
dispatch_sync调度队列上的块并等待块完成。很明显,这极大地限制了并发性。您应该几乎总是使用dispatch_async。
顺序队列一次只能执行一个块。很明显,这极大地限制了并发性。当您需要一个接一个地执行各种块时,顺序队列仍然很有用,并且它们可以与其他队列中的块同时执行。
因此,为了最大限度地使用处理器,请在并发队列上使用dispatch_async。并且不需要创建多个并发队列。它是并发的。它可以同时运行任意数量的块。