iOS多线程系统整理 swift
多线程 是一个应用程序内多个代码的执行路径,执行线程,同时在同一时间里执行不同的任务。
三种:
1、NSTread
2、Cocoa NSOperation (NSOperation,NSOperationQueue)
3、GrandCentralDispatch:GCD
1\NSTread
相对最简单,需要自己管理线程的生命周期和线程同步(加锁会有一定的系统开销)
两种应用方式:
需要传递三个参数:
selector:线程执行方法""
target:方法所在的对象
argument:传递给方法的参数,可选nil
一、直接创建线程,自动运行线程
// Class Method
class func detachNewThreadSelector(selector:Selector,toTarget target:AnyObject,withObject argument:AnyObject?)
二、先创建一个线程对象,手动运行线程,在运行之前可设置线程优先级等信息。
convenience init(target:AnyObject,selector:Selector,object argument:AnyObject?)
for example
// download image method
func downloadImage()
{
var imageUrl = "https://www.baidu.com/img/bdlogo.png"
var data = NSData.dataWithContentsOfURL(NSURL.URLWithString(imageUrl),options:nil,error:nil)
println(data.length)
}
override func viewDidLoad(){
super.viewDidLoad()
// 第一种方式
NSThread.detachNewThreadSelector("downloadImage",toTarget:self,withObject:nil)
// 第二种方式
var downloadImageThread = NSThread(target:self,selector:"downloadImage",object:nil)
dowloadImageThread.start()
}
线程同步,通过锁来实现,每个线程有一个锁,锁 与 特定的线程关联。
for example
// 定义两个线程
var thread1,thread2:NSThread?
// 线程条件
let condition1 = NSCodition()
let condition2 = NSCodition()
// two method for thread
func method1(sender: AnyObject)
{
for var i = 0; i <10; i++
{
println("thread 1 running \(i)")
sleep(1)
if i == 2
{
thread2!.start()
// lock
condition1.lock()
condition1.wait()
condition1.unlock()
}
}
println(thread 1 over)
//
condition2.signal()
}
//
func method2(sender:AnyObject)
{
for var i=0;i<10;i++
{
println("thread 2 running \(i)")
sleep(1)
if i ==2
{
// active thread 1
condition1.signal()
// lock
condition2.lock()
condition2.wait()// stop waitting
condition2.unlock()
}
}
println("thread 2 over")
}
// RUN
thread2 = NSThread (target:self , selector:"method2:",object:nil)
thread1 = NSThread(target:self,selector:"method1",object:nil)
控制台输出
thread 1 running 0
thread 1 running 1
thread 1 running 2
thread 2 running 0
thread 2 running 1
thread 2 running 2
thread running 3
thread 1 running 4
thread 1 running 5
thread 1 running 6
thread 1 running 7
thread 1 running 8
thread 1 running 9
thread 1 over
thread 2 running 3
thread 2 running 4
thread 2 running 5
thread 2 running 6
thread 2 running 7
thread 2 running 8
thread 2 running 9
线程1 2是同步关系,启动2,挂起 1,激活1,挂起2,有效避免了线程1占用一个资源时,引起线程2不能访问的问题。
NSOperation 两种方式
一 两个子类 NSInvocationOperation NSBlockOperation
// creat instance
var operation = NSInvocationOperation(target:self,selector:"dowloadImage",object:nil)
var queue = NSOperationQueue()
queue.addOperation(operation)
后台建立一个线程
Queue队列中可以加入很多个operation 可以把它看做是一个线程池子,可以设置线程池中的线程数,即并发操作数。
默认是:-1,-1表示没有限制,同时运行队列中的全部操作。
queue.maxConcurrentOperationCount = 6
// ervery operation come to an end
var completionBlock:(()->Void)?
operation.completionBlock = completionBlock
dispatch_after(dispatch_time(DISPATCH_TIME_NOW,4),dispatch_get_main_queue(),{println("complete")})
// cancell
queue.cancelAllOperations()
二 继承NSOperation 把子类的对象放到NSOperationQueue队列中 ,一旦加入,就处理这个,直到操作完成,队列被释放。
// creat DrinkOperation.swift 继承 NSOperation 且 实现main方法
import UIKit
class DrinkOperation:NSOperation{
override func main()
{
println("drink")
}
}
// e.g.
// creat a instance
var queue1 = NSOperationQueue()
// creat a operation
var drinkOperation = DrinkOperation()
// add
queue1.addOperation(drinkOperation)
Grand Central Dispatch
多核编程
底层也是用线程实现,queue可以接受任务,先到先执行顺序来执行,也可以并发或串行执行。
同步或异步
优点多多:基于C,融入面向对象,Block,易用,性能上自动根据系统负载来增减线程数量,无需加锁。
三种方法:
一 自己创建队列
func dispatch_queue_create(label:UnsafePointer<Int8>,attr:dispation_queue_attr_t!)->dispatch_queue_t!
label:参数代表队列名称,可以任意名
DISPATCH_QUEUE_CONCURRENT 并行
DISPATCH_QUEUE_SERIAL 串行
//e.g.
var serialQueue = dispatch_queue_create("serialQueue_1",DISPATCH_QUEUE_SERIAL)
var concurrentQueue = dispatch_queue_create("concurrentQueue_1",DISPATCH_QUEUE_CONCURRENT)
二 获取系统的全局队列
func dispatch_get_global_queue(identifier:Int,flags:UInt)->dispatch_gueue_t!
参数 identifier 执行优先级 ,4个优先级
DISPATCH_QUEUE_PRIORITY_HIGH
DISPATCH_QUEUE_PRIORITY_DEFAULT
DISPATCH_QUEUE_PRIORITY_LOW
DISPATCH_QUEUE_PRIORITY_BACKGROUND 非常低的有相机,用于不太关心的后台任务
// e.g.
var globalQueue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT,0)
三 在主线程的Main dispatch queue
在主线程里执行的队列(只有一个主线程)
一切跟UI相关的操作都放到主线程中执行
func dispatch_get_main_queue()->dispatch_queue_t!
// e.g.
var mainQueue = dispatch_get_main_queue()
追加任务到队里的 两个方法:
一 dispatch_async 异步追加Block
async = asynchronous 异步
func dispatch_async(queue:dispatch_queue_t!,block:dispatch_block_t!)
第一个参数:GCD队列
第二个参数:block
// e.g.
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT,0),{()->Void in
// 耗时代码块
//执行完 调用主线程刷新界面
dispatch_async(dispatch_get_main_queue(),{()->Void in
//通知主线程刷新
})
})
二 dispatch_sync 同步追加Block
与之前相反,block结束之前,dispatch_sync会一直等待,等待队列前面的所有任务完成后才执行追加的任务。
func dispatch_sync()
// e.g.
dispatch_sync(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT,0),{()->Void in
println("sync1")
})
加到 global_queue异步队列中,不会造成锁死,但会一直等待代码执行完毕。
如果加到main_queue中,在主线程中添加任务操作,就会引起死锁。
// e.g.
dispatch_sync(dispatch_get_main_queue(),{()->Void in
print("sync2")
})
暂停和继续执行队列
func dispatch_suspend() 暂停
func dispatch_resume() 继续
suspend 使 suspension reference count +1
resume -1
count>0 queue就保持挂起状态
如果挂起了 一个 queue 或者 source 那么销毁他之前,先对其进行恢复。
var concurrentQueue = dispatch_queue_create("concurrentQueue_1",DISPATCH_QUEUE_CONCURRENT)
// stop
dispatch_suspend(concurrentQueue)
// go on
dispatch_resume(concurrentQueue)
只执行一次 用于单例
dispatch_once
延时:指定时间后把任务追加到 dispatch queue里面
dispatch_after
func dispatch_time(when:XX,delta:Int64)->dispatch_time_t
delta单位非常小,到秒要乘以 NSEC_PER_SEC
let deltaT = 2.0 *Double(NSEC_PER_SEC)
let dTime =dispatch_time(DISPATCH_TIME_NOW,Int64(deltaT))
dispatch_after(dTime,dispatch_get_global-global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT,0)
{()->Viod in
println("延时2秒执行")
})
多个任务都结束的一个全部结束:dispatch_barrier_async
当执行任务更新数据时,会出现数据不一样的情况。
for i in 1...100
{
dispatch_async(queue,{()->Void in
println("\(i)")
})
}
虽然使用dispatch_barrier_async可以避免
但是有另一方法, semaphore 信号量
var semaphore = dispatch_semaphore_creat(1)//初始值为1
for i in 1...100
{
dispatch_async(queue,{()->Void in
dispatch_semaphore_wait(semaphore,DISPATCH_TIME_FOREVER)
println("\(i)")
dispatch_semaphore_signal(semaphore)
})
}
iOS多线程系统整理 swift的更多相关文章
- 关于iOS多线程的总结
关于iOS多线程的总结 在这篇文章中,我将为你整理一下 iOS 开发中几种多线程方案,以及其使用方法和注意事项.当然也会给出几种多线程的案例,在实际使用中感受它们的区别.还有一点需要说明的是,这篇 ...
- iOS多线程(转)
关于iOS多线程,你看我就够了 字数8596 阅读28558 评论74 喜欢313 在这篇文章中,我将为你整理一下 iOS 开发中几种多线程方案,以及其使用方法和注意事项.当然也会给出几种多线程的案例 ...
- iOS多线程
关于iOS多线程 概述 这篇文章中,我不会说多线程是什么.线程和进程的区别.多线程有什么用,当然我也不会说什么是串行.什么是并行等问题,这些我们应该都知道的. 在 iOS 中其实目前有 4 套多线程方 ...
- iOS 多线程 浅述
什么是进程? 进程是指在系统中正在运行的一个应用程序. 每个进程之间是独立的,每个进程均运行在其专用且受保护的内存空间内. 什么是线程? 1个进程要想执行任务,必须得有线程(每1个进程至少要有1条线程 ...
- iOS多线程编程
废话不多说,直接上干货.先熟悉一下基本知识,然后讲一下常用的两种,NSOperation和GCD. 一.基础概念 进程: 狭义定义:进程是正在运行的程序的实例(an instance of a com ...
- iOS多线程--深度解析
多线程 你们项目中为什么多线程用GCD而不用NSOperation呢? 你有没有发现国外的大牛他们多线程都是用NSOperation? 你能告诉我他们这样做的理由吗? 关系: ①:先搞清两者的关系,N ...
- iOS 资源大全整理
这是个精心编排的列表,它包含了优秀的 iOS 框架.库.教程.XCode 插件.组件等等. 这个列表分为以下几个部分:框架( Frameworks ).组件( Components ).测试( Tes ...
- iOS多线程编程(四)------ GCD(Grand Central Dispatch)
一.简单介绍 是基于C语言开发的一套多线程开发机制.也是眼下苹果官方推荐的多线程开发方法.用起来也最简单.仅仅是它基于C语言开发,并不像NSOperation是面向对象的开发.而是全然面向过程的.假设 ...
- iOS 多线程的使用
iOS 多线程 先看一篇阮一峰写关于进程和线程的文章,快速了解线程的相关概念. 随着现在计算机硬件的发展,多核心.高频率的cpu越来越普及,为了充分发挥cpu的性能,在不通的环境下实现cpu的利用最大 ...
随机推荐
- 基于OpenCV之视频读取,处理和显示框架的搭建(一)
主要包括以下内容: 1.使用的主要函数的说明. 2.两个实例:视频读取和显示.搭建视频读取和处理框架,调用canny函数提取边缘并显示. 3.一些注意事项和代码说明. 一.使用的主要函数 1.延时函数 ...
- IO系列之File
1 File类 1.1 目录列表器 在这里我主要是参考Think in Java的内容从而做的一些总结以及扩展.Java中的IO流的设计应该说是Java中最经典的,最学院式的设计,包括它的整体架构设计 ...
- JVM原理解析
JVM主要的功能: 内存分配 程序调度 内存释放(栈等自动释放.堆垃圾回收) 异常处理 https://www.cnblogs.com/dingyingsi/p/3760447.html https: ...
- R中的统计模型
R中的统计模型 这一部分假定读者已经对统计方法,特别是回归分析和方差分析有一定的了解.后面我们还会假定读者对广义线性模型和非线性模型也有所了解.R已经很好地定义了统计模型拟合中的一些前提条件,因此我们 ...
- p4180 次小生成树
传送门 分析: 次小生成树的求法有两种,最大众的一种是通过倍增LCA找环中最大边求解,而这里我介绍一种神奇的O(nlogn) 做法: 我们先建立最小生成树,因为我们用kruskal求解是边的大小已经按 ...
- c++中placement new
c++中的placement new是::operator new的重载版本,用于在已经分配好的内存上创建对象.这样就可以在用户空间对内存进行操作,减少了对象生成的成本,控制对象的地址从而减少内存碎片 ...
- 6.wireshark使用全解
开始之前先推荐一个wireshark视频: http://www.shiyanbar.com/course-video/watchVideo/cid/419/vid/2001 页面功能简介 1.主界面 ...
- Good Bye 2014 B. New Year Permutation(floyd )
题目链接 题意:给n个数,要求这n个数字小的尽量放到前面,求一个最小的. 给一个矩阵s[i][j]==1,表示位置 i 的数字可以和 位置 j 的数字交换. 分析: 刚开始用的是3个循环,每次都找一个 ...
- 微信小程序自学第三课:文件作用域,模块化
一.文件作用域 在 JavaScript 文件中声明的变量和函数只在该文件中有效:不同的文件中可以声明相同名字的变量和函数,不会互相影响. 通过全局函数 getApp() 可以获取全局的应用实例,如果 ...
- 【IDEA下使用tomcat部署web项目】
1.IDEA下的WEB项目新建就不说了. 2.配置tomcat:file-->settings-->Build,Execution,Deployment-->Application ...