专栏名称: 程序员大咖
为程序员提供最优质的博文、最精彩的讨论、最实用的开发资源;提供最新最全的编程学习资料:PHP、Objective-C、Java、Swift、C/C++函数库、.NET Framework类库、J2SE API等等。并不定期奉送各种福利。
目录
相关文章推荐
程序员小灰  ·  以后是彻彻底底的小生意时代 ·  23 小时前  
老刘说NLP  ·  RAG&KG&LLM&文档智能四大领域技术前 ... ·  昨天  
程序员的那些事  ·  阿里云核心域名竟遭劫持,博客园等众多网站瘫痪 ... ·  2 天前  
程序员的那些事  ·  不到 2 个月,OpenAI 火速用 ... ·  4 天前  
51好读  ›  专栏  ›  程序员大咖

Swift多线程:GCD进阶,单例、信号量、任务组

程序员大咖  · 公众号  · 程序员  · 2017-08-07 19:31

正文

请到「今天看啥」查看全文


//Creates a `DispatchTime` relative to the system clock that ticks since boot.

let time = DispatchTimeInterval.seconds(3)

let delayTime: DispatchTime = DispatchTime.now() + time

DispatchQueue.global().asyncAfter(deadline: delayTime) {

Thread.current.name = "dispatch_time_Thread"

print("Thread Name: (String(describing: Thread.current.name)) dispatch_time: Deplay (time) seconds. ")

}

}


方法二:使用绝对时间,DispatchWallTime


@IBAction func delayProcessDispatchWallTime(_ sender: Any) {

//dispatch_walltime用于计算绝对时间。

let delaytimeInterval = Date().timeIntervalSinceNow + 2.0

let nowTimespec = timespec(tv_sec: __darwin_time_t(delaytimeInterval), tv_nsec: 0)

let delayWalltime = DispatchWallTime(timespec: nowTimespec)

//wallDeadline需要一个DispatchWallTime类型。创建DispatchWallTime类型,需要timespec的结构体。

DispatchQueue.global().asyncAfter(wallDeadline: delayWalltime) {

Thread.current.name = "dispatch_Wall_time_Thread"

print("Thread Name: (String(describing: Thread.current.name)) dispatchWalltime: Deplay (delaytimeInterval) seconds. ")

}

}


3
队列的循环、挂起、恢复


3.1 dispatch_apply


dispatch_apply函数是用来循环来执行队列中的任务的。在Swift 3.0里面对这个做了一些优化,使用以下方法:


public class func concurrentPerform(iterations: Int, execute work: (Int) -> Swift.Void)


本来循环执行就是为了节约时间的嘛,所以默认就是用了并行队列。我们尝试一下用这个升级版的dispatch_apply让它执行10次打印任务。


@IBAction func useDispatchApply(_ sender: Any) {


print("Begin to start a DispatchApply")

DispatchQueue.concurrentPerform(iterations: 10) { (index) in

print("Iteration times:(index),Thread = (Thread.current)")

}

print("Iteration have completed.")


}


运行结果如下:



看,是不是所有的任务都是并行进行的?标红的地方,是非典型技术宅想提醒一下大家这里还是有一些任务是在主线程中进行的。它循环执行并行队列中的任务时,会开辟新的线程,不过有可能会在当前线程中执行一些任务。


如果需要循环的任务里面有特别耗时的操作,我们上一篇文章里面说是应该放在global里面的。如何避免在主线程操作这个呐???


来,给三秒时间想想。

看到调用这个方法的时候是不是就是在UI线程里面这么写下来的嘛?那就开启一个gloablQueue,让它来进行不就好了嘛!BINGO!

这位同学,你已经深得真谛,可以放学后到我家后花园来了。嘿嘿✧(≖ ◡ ≖✿)嘿嘿







请到「今天看啥」查看全文