加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 百科 > 正文

SQLite的并发处理

发布时间:2020-12-12 20:04:59 所属栏目:百科 来源:网络整理
导读:?? 使用SQLite经常会遇到并发处理,要处理好多线程或多进程之间的并发,就得搞清楚SQLite的机制,尤其是Sqlite的锁机制。 因为SQLite是文件数据库,所以它的锁也基本是和文件一致,也即: 写独占,读共享。 这意味是在读取数据库的时候,是可以多个线程共享
?? 使用SQLite经常会遇到并发处理,要处理好多线程或多进程之间的并发,就得搞清楚SQLite的机制,尤其是Sqlite的锁机制。

因为SQLite是文件数据库,所以它的锁也基本是和文件一致,也即:写独占,读共享。这意味是在读取数据库的时候,是可以多个线程共享的,而如果有增删改的操作,则会独占此文件,其他线程会进程都会被阻塞。

在移动设备上,比较常见的情况是App的UI进程和Service进程同时访问数据库,这个时候就要对其访问做好并发的处理,否则会出现很多意想不到的后果。


对于每个SQLite的API执行,都需要妥善处理返回值,尤其是SQL_BUSY的时候。

当一个线程独占数据库时,其他线程无论是查询还是写入,都可能返回SQL_BUSY,这个时候,有几种处理方式:

1,使用操作系统的锁,比如信号量和Mutex,把执行写入的操作代码框在临界区内。

HANDLE hMutex =NULL;

hMutex = CreateMutex(NULL,TRUE,NULL);

WaitForSingleObject(hMutex,INFINITE);

sqlite operation;

ReleaseMutex(hMutex);

2,让其他线程在遇到SQL_BUSY的时候重试。

Exec:

int nRet = sqlite3_exec(db,sql,NULL,errmsg);

if(nRet== SQL_BUSY)

{
    sleep(100);
    goto Exec;

}

注意个人设置重试次数,以免死锁。


3,经测试,在显式地开启了事务后,其他线程似乎会默认等待,到事务执行完成后再进入临界区。相当于sqlite引擎做了第1种方案做的事。

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读