使用SQLite在Python中使用查询结果创建新表的速度很慢

时间:2015-04-13 17:28:24

标签: python sqlite

使用Python,我尝试从查询结果在数据库中创建一个新的SQLite表,该查询结果在该数据库中的另外两个表上执行。

对于记录,查询是

CREATE TABLE results AS

    SELECT table_1.*, table_2.*
    FROM table_1
        LEFT JOIN table_2
            ON table_1.ID_1 = table_2.ID_2
    UNION ALL
    SELECT table_1.*, table_2.*
    FROM table_2
        LEFT JOIN table_1
            ON table_1.ID_1 = table_2.ID_2
    WHERE table_1.ID_1 IS NULL

这应该是FULL OUTER JOIN的一种解决方法,它在SQLite中不能直接使用(这个方法可以在这个主题的不同SO线程上找到)。

然而,这个操作在我的桌子上运行很慢,每个行大约有100万行......这么慢,我得到的印象是,在资源管理器窗口中点击刷新时会花费数小时来显示更新时的数据库文件大小。

我怎样才能更快地获得这个?我已经对此进行了大量研究,大多数时候,人们都在谈论使用事务,否则,每一行都会打开一个新的数据库连接或者其他......但是,我找不到一个有效的例子如何使用它。

到目前为止我的两种方法太慢了:

使用Python的sqlite3模块:

# open sqlite database
conn = sqlite3.connect('Database.sqlite')

# get a cursor
cursor = conn.cursor()

# start query
cursor.execute("""
CREATE TABLE results AS
    SELECT table_1.*, table_2.*
    FROM table_1
        LEFT JOIN table_2
            ON table_1.ID = table_2.ID
    UNION ALL
    SELECT table_1.*, table_2.*
    FROM table_2
        LEFT JOIN table_1
            ON table_1.ID = table_2.NETWORK_ID
    WHERE table_1.ID IS NULL
;""")

使用sqalchemy

from sqlalchemy import create_engine, event
from sqlite3 import dbapi2 as sqlite

# create database engine
engine = create_engine('sqlite:///Database.sqlite')

# open sqlite database
connection = engine.connect()

# query
with connection.begin() as trans:
    connection.execute("BEGIN TRANSACTION;")

    connection.execute("""
    CREATE TABLE results AS

        SELECT table_1.*, table_2.*
        FROM table_1
            LEFT JOIN table_2
                ON table_1.ID = table_2.ID
        UNION ALL
        SELECT table_1.*, table_2.*
        FROM table_2
            LEFT JOIN table_1
                ON table_1.ID = table_2.ID
        WHERE table_1.ID IS NULL
    ;""")

    trans.commit()

1 个答案:

答案 0 :(得分:0)

哎呀...问题不在于上面的代码,而在于提供JOIN输入的表格。我在创建它时缺乏准确性,因此ID的{​​{1}}列的类型为table_1,而INTEGER的{​​{1}}列的类型为ID

不幸的是,对不同类型的列进行JOIN不会产生错误 - 相反,我想在内部发生非常昂贵的事情就像将每个table_2转换为STRING,比较然后再回到STRING,反之亦然。

所以,故事的寓意:如果INTEGER中的STRING非常缓慢,请检查CREATE TABLE列的数据类型是否相等。