SQLite多线程写锁文件解决方案
发布时间:2020-12-13 00:19:16 所属栏目:百科 来源:网络整理
导读:在sqlite编程中多线程同时写时会出现异常,我写了个类来解决这个问题。 思路很简单,就是在开始写操作时,记下写操作的托管线程id,表示目前有线程正在做写操作;其他线程来写时,需要先检测是否有进程正在做写操作,如果有就需要等待,等待到某一个配置的超
在sqlite编程中多线程同时写时会出现异常,我写了个类来解决这个问题。 思路很简单,就是在开始写操作时,记下写操作的托管线程id,表示目前有线程正在做写操作;其他线程来写时,需要先检测是否有进程正在做写操作,如果有就需要等待,等待到某一个配置的超时时间时,会抛出异常终止等待;如果没有则直接放行,此线程可以获得写锁。最后写操作执行完毕时需要释放锁。 下面是具体的代码: ///<summary>///用于在多线程访问sqlite时防止同步写导致锁文件 /// ///使用方法: ///using(SQLiteWriteLocksqliteLock=newSQLiteWriteLock(SQLite链接字符串)) ///{ /////sqlite写操作代码 ///} /// ///可以通过在配置文件appSettings节中添加设置SQLiteWriteLockTimeout的value值控制锁等待的超时时间,该值必须为正整数数字,单位为毫秒, ///默认的超时时间是1000ms ///</summary> publicsealedclassSQLiteWriteLock:IDisposable { #region静态字段和属性 constshortWAIT_TIME=5; staticreadonlyobjectlocker=newobject(); staticDictionary<string,int>_dbThreadIdDict=newDictionary<string,int>(); ///<summary> ///获得写操作的超时时间,单位为毫秒,可以通过配置文件appSettings节中添加设置SQLiteWriteLockTimeout的value值控制锁等待的超时时间,该值必须为正整数数字,单位为毫秒 ///默认的超时时间是1000ms ///</summary> publicstaticintSQLiteWriteLockTimeout { get { stringconfigValule=ConfigurationManager.AppSettings["SQLiteWriteLockTimeout"]; if(!string.IsNullOrEmpty(configValule)) { returnint.Parse(configValule); } return1000; } } #endregion privatereadonlystring_connString; //隐藏无参构造函数 privateSQLiteWriteLock(){} publicSQLiteWriteLock(stringconnString) { _connString=connString; AcquireWriteLock(); } #region私有方法 privatevoidAcquireWriteLock() { intthreadId=Thread.CurrentThread.ManagedThreadId; intwaitTimes=0; while(_dbThreadIdDict.ContainsKey(_connString)&&_dbThreadIdDict[_connString]!=threadId) { Thread.Sleep(WAIT_TIME); waitTimes+=WAIT_TIME; #ifDEBUG Console.WriteLine(_connString+"waitfor"+waitTimes+"ms"); #endif if(waitTimes>SQLiteWriteLockTimeout) { thrownewTimeoutException("SQLite等待写操作超时"); } } lock(locker) { if(!_dbThreadIdDict.ContainsKey(_connString)) _dbThreadIdDict.Add(_connString,threadId); } } privatevoidReleaseWriteLock() { lock(locker) { if(_dbThreadIdDict.ContainsKey(_connString)) { _dbThreadIdDict.Remove(_connString); } } } #endregion #regionIDisposable成员 publicvoidDispose() { ReleaseWriteLock(); } #endregion } 请尊重作者的劳动,转载请保留链接玉开的技术博客 (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |