【发布时间】:2014-12-07 11:08:08
【问题描述】:
我对此进行了很多搜索,但运气不佳。作为测试,我编写了一个 C# WinForms 应用程序,我在其中启动了可配置数量的线程,并让每个线程将可配置数量的数据写入该线程创建的 SQLite 数据库中的多个表中。因此,每个线程都会创建自己的 SQLite 数据库,并且只有该线程与之交互。
我看到的是,由于并发性,肯定会发生一些性能下降。例如,如果我大致同时启动每个线程,则写入 SQLite 表的性能会下降,而如果我在每个线程中设置随机启动延迟以分散它们的访问权限。
SQLite 的启动速度非常快,足以满足我的测试需求,我可以在 1/3 秒内将 20,000 行插入表中,但是一旦我启动 250 个线程,同样的 20,000 行可能需要 MINUTES 才能写入每个数据库。
我已经尝试了很多东西,包括定期提交、设置 Sychronous=Off、使用参数化查询等等……所有这些都有助于缩短每条语句所花费的时间(从而减少并发活动),但没有什么能真正解决它,我希望有人能给一些建议。
谢谢! 安迪
【问题讨论】:
-
你的意思是,多个线程同时写入磁盘上不同的地方比单个线程慢?
-
您对这一级别的并发写入同一磁盘的性能有何期望?
-
多个线程,每个线程都写入他们通过自己的 SQLite 连接创建的自己的 SQLite 数据库,比单个线程写入单个 SQLite 数据库要慢得多。我显然预计它会更慢,有更多的 CPU 使用率、内存使用率等......但性能肯定会出现爆炸性的争用惩罚,这似乎表明 SQLite 在内部的某个地方存在共享资源。
-
我同意。我使用平面文件用 C# 编写了一个快速测试用例,250 名工作人员每人编写了 65k 条记录。如果没有锁定,所有写入都在大约一秒钟内完成,锁定所有写入大约在 16 秒内完成(SATA3 SSD 为 18 秒,比 WD Green 2TB 慢得多)。我希望 SQLite 案例比这慢,但不超过 2*N 或 3*N,但这只是一个毫无头绪的猜测。我假设争用发生在库本身,与使用单个进程处理 250 个数据库/事务有关。我会尝试一种多进程方法,看看你是否发现了差异。
标签: c# sqlite concurrency