IOS异步和多线程操做&&在sqlite3中的应用

1,数据库I/O操做(异步)html

数据库自己是存储在磁盘上。访问和修改数据库,即对磁盘进行读写,即I/O操做。sql

磁盘属于计算机硬件,具备DMA能力,不须要CPU干预,能够实现异步操做。数据库

I/O操做通常是消耗时间,sqlite使用异步处理I/O操做。安全

当有多个事务对数据库进行操做,对应,也会有多个I/O操做。多线程

操做系统将I/O操做,合理放入一个I/O队列。一次性将队列内的I/O操做提交给磁盘系统,并行处理多个I/O,提升效率。详细请看连接,本人也没有特别深刻研究。并发

2,异步和多线程iphone

异步和多线程,都有能力实现,不阻塞当前线程,使应用更“流畅”。 IOS最多见的, 不阻塞主线程,使UI表现更流畅。异步

二者有区别。 具体请看连接。atom

总之,异步的实现,是基于计算机硬件的支持,而多线程,是操做系统中,一段逻辑代码控制的。url

3,线程安全以及处理

当一段代码或者某个变量,被多个线程同时访问和使用。 这些代码或者变量,可能会出现非预期的效果,好比数据紊乱和数据安全的问题,这是“非安全的”。

为了线程安全, 须要在同一时刻,只能有一个线程访问这些代码或者变量,IOS中使用“互斥锁”,来避免这个状况。

(互斥,mutex,从自己词语意思:不相容,互相排斥的。数学上,A和B互斥, 指A和B没有任何交集。 A和B不能同时发生。)

“互斥锁”即@synchronized(对象A) {} ,对象A,只能被一个线程访问。

所以,若是使用“互斥锁”,必定是在, 多个线程,同时访问一份资源的状况。

互斥锁,增长了CPU的开销。IOS中,atomic,就是为 setter 方法增长“互斥锁”。比不要的状况下,必定要使用“nonatomic”。

4,sqlite3以及sqlite3的多线程

sqlite3是轻量级的数据库。sqlite3一样使用异步I/O操做,来读取数据。关于sqlite3异步I/O操做,具体请看连接

IOS中的sqlite3是线程安全的。IOS中UI在主线程,不阻塞UI线程,保证流畅,因此把sqlite的操做,须要迁移到子线程。这是sqlite3使用多线程的主要驱动力。

有一篇很好的文章,具体点击连接

  • (1),单线程:禁用全部的mutex锁,并发使用时会出错。当SQLite编译时加了SQLITE_THREADSAFE=0参数,或者在初始化SQLite前调用sqlite3_config(SQLITE_CONFIG_SINGLETHREAD)时启用。
  • (2),多线程:只要一个数据库链接不被多个线程同时使用就是安全的。源码中是启用bCoreMutex,禁用bFullMutex。实际上就是禁用数据库链接和prepared statement(准备好的语句)上的锁,所以不能在多个线程中并发使用同一个数据库链接或prepared statement。当SQLite编译时加了SQLITE_THREADSAFE=2参数时默认启用。若SQLITE_THREADSAFE不为0,能够在初始化SQLite前,调用sqlite3_config(SQLITE_CONFIG_MULTITHREAD)启用;或者在建立数据库链接时,设置SQLITE_OPEN_NOMUTEX flag。
  • (3),串行:启用全部的锁,包括bCoreMutex和bFullMutex。由于数据库链接和prepared statement都已加锁,因此多线程使用这些对象时无法并发,也就变成串行了。当SQLite编译时加了SQLITE_THREADSAFE=1参数时默认启用。若SQLITE_THREADSAFE不为0,能够在初始化SQLite前,调用sqlite3_config(SQLITE_CONFIG_SERIALIZED)启用;或者在建立数据库链接时,设置SQLITE_OPEN_FULLMUTEX flag。

IOS中的sqlite,默认使用(2)的配置。不方便的是,若是要被另外的线程访问sqlite,其余的就必须关闭数据库链接。 代码中就有不少不方便的地方。

配置(1)不考虑,为单线程。

配置(3),将多线程变串行方式执行,

(暂停。。)

相关文章
相关标签/搜索