APSW(或 SQLite3)在 executemany 上插入非常慢

Yon*_*ona 3 python sqlite apsw

插入行时,我发现 APSW(Python 的 SQLite 解析器)存在以下问题。

假设我的数据是 data = [[1,2],[3,4]]

APSW 和 SQLite3 允许我执行以下操作:

apsw.executemany("INSERT INTO Table VALUES(?,?)", b)
Run Code Online (Sandbox Code Playgroud)

或者我可以编写一些代码来执行以下操作:

sql = "BEGIN TRANSACTION; 
INSERT INTO Table Values('1','2');
INERT INTO Table Values('3','4');
COMMINT;"

apsw.execute(sql)
Run Code Online (Sandbox Code Playgroud)

data是一个长列表/数组/表时,第一种方法的性能与第二种方法相比非常慢(对于 400 行,它可以是 20 秒,而小于 1!)。我不明白为什么会这样,因为这是所有 SQLite Python 教程中显示的将数据添加到表中的方法。

知道这里可能发生什么吗?

Rog*_*nns 8

(披露:我是 APSW 的作者)。如果你没有明确地有一个有效的事务,那么 SQLite 会自动在每条语句的开头启动一个,并在每条语句的末尾结束。写入事务是持久的——这意味着内容必须以存储和 fsync 结束,以确保它们能够在意外电源或系统故障时幸免于难。存储速度慢!

我建议with在您的情况下使用而不是 BEGIN/COMMIT,因为它会自动回滚错误。这确保您的数据插入要么完全发生,要么根本不发生。有关示例,请参阅文档

当您插入大量数据时,您会发现WAL 模式的性能更高。


Yon*_*ona 7

感谢Confuseh,我得到了以下答案:

执行:

apsw.execute("BEGIN TRANSACTION;")
apsw.executemany("INERT INTO Table VALUES(?,?)", b)
apsw.execute("COMMIT;")
Run Code Online (Sandbox Code Playgroud)

大大加快了进程!这似乎是添加数据的正确方法(与使用我创建多个 INSERT 语句的方法相比)。