Android 最近插入时,SQLite选择非常慢

Android 最近插入时,SQLite选择非常慢,android,sqlite,android-sqlite,sqlcipher,Android,Sqlite,Android Sqlite,Sqlcipher,我有一张大约700万行的桌子。我平均每秒向数据库中插入一行。当我这样做时,我注意到对数据库运行简单的SELECT需要非常长的时间(多达15秒),例如: SELECT * FROM table WHERE rowid > 7100000 此选择通常不返回任何数据行,因为有时在此特定表中未插入任何数据。这种情况经常发生,即使我正在写入的表甚至没有在我正在读取的表中插入行 其思想是有两个独立的过程,一个是添加数据,另一个是尝试获取所有尚未读取的新数据。但是读取端连接到用户界面,任何明显的延迟都

我有一张大约700万行的桌子。我平均每秒向数据库中插入一行。当我这样做时,我注意到对数据库运行简单的SELECT需要非常长的时间(多达15秒),例如:

SELECT * FROM table WHERE rowid > 7100000
此选择通常不返回任何数据行,因为有时在此特定表中未插入任何数据。这种情况经常发生,即使我正在写入的表甚至没有在我正在读取的表中插入行

其思想是有两个独立的过程,一个是添加数据,另一个是尝试获取所有尚未读取的新数据。但是读取端连接到用户界面,任何明显的延迟都是无法忍受的,更不用说15秒了。这是在安卓系统下运行的,用户界面线程也不喜欢被阻塞那么长时间,这造成了巨大的破坏

我最初的想法是,插入可能需要更新标记,因为最初我在不同的字段(时间字段)上有索引。这似乎至少部分得到了证实,因为如果我使用一个只有几行的数据库,每个select都会在几毫秒内完成。但是,当我重新创建表以仅将rowid作为主键时,它实际上变慢了。我希望在末尾插入一个新行时,只要将rowid作为主键进行比较,读取速度就会非常快

我已经尝试过启用预写日志记录,但SQLCipher似乎不支持这一点,至少不直接支持,因为它不符合android.database.sqlite.SQLiteDatabase的最新API。即使在postKey钩子中使用“PRAGMA journal_mode=WAL”也没有任何区别

这是怎么回事?如何加快我的选择


更新:我试着摆脱sqlcipher,只是使用普通sqlite看看这是否是一个因素。我使用sqlcipher_export导出到纯文本数据库,然后使用默认的
android.database.sqlite.sqlcipher
。延迟时间从10-20秒下降到1.8-2.8秒。然后,我删除了预写,它进一步下降到1.3-2.7秒。因此,问题仍然存在,尽管它确实得到了很大改善。

SQLite最终是基于文件的,并且没有可移植的机制来与另一个进程通信文件的哪一部分发生了更改。因此,当一个进程写入了某些内容时,所有其他进程在下次访问数据库文件时都必须删除缓存

如果可能,请修改您的体系结构,使代码的两个部分处于相同的进程中,并共享相同的数据库连接。(对于多线程,这需要锁定,但SQLite没有多少并发性。)

或者,将新数据写入单独的数据库,并让UI应用程序将其移动到自己的数据库中


我不知道为什么SQLCipher会慢得多(这不太可能是解密的CPU开销)。

我将首先确定并发插入对应用程序和查询的影响。换句话说,禁用插入新数据,并测量同一select语句运行所需的时间。此外,了解一次插入多少行以及该操作是否在事务中运行也会很有帮助。