【问题标题】:Inserting multiple rows using psycopg2使用 psycopg2 插入多行
【发布时间】:2014-04-27 08:43:12
【问题描述】:

根据psycopg2: insert multiple rows with one query,使用psycopg2的execute而不是executemany效率更高。其他人可以确认吗?

上述 StackOverflow 问题建议使用 mogrify 来创建此类语句:

INSERT INTO table VALUES (value1, value2), (value3, value4)

是否可以使用常规的execute 函数生成这样的语句?我想到了一些形式

cursor.execute("""INSERT INTO table VALUES (%s, %s), (%s, %s)""", ((value1,value2),(value3,value4)))

会起作用的。

更新:

例如,我尝试将我传入执行 sql 语句:

insert into history (timestamp) values (%s),(%s); 

使用以下元组:

(('2014-04-27 14:07:30.000000',), ('2014-04-27 14:07:35.000000',))

但我得到的只是错误:

没有要获取的结果

【问题讨论】:

  • 你没有先尝试这个?
  • 多值插入确实比psycopg2 中的executemany 更有效,尽管只是在一定程度上——如果您在每个语句中插入数万行,内存使用就会成为问题.几百或几千的批次(如果行更小)就可以了。

标签: python postgresql psycopg2 python-db-api


【解决方案1】:

要使用 execute 方法,将要插入的数据放在一个列表中。列表将由 psycopg2 调整为数组。然后你取消嵌套数组并根据需要转换值

import psycopg2

insert = """
    insert into history ("timestamp")
    select value
    from unnest(%s) s(value timestamp)
    returning *
;"""

data = [('2014-04-27 14:07:30.000000',), ('2014-04-27 14:07:35.000000',)]
conn = psycopg2.connect("host=localhost4 port=5432 dbname=cpn")
cursor = conn.cursor()
cursor.execute(insert, (data,))
print cursor.fetchall()
conn.commit()
conn.close()

不确定与 executemany 的性能差异是否很大。但我认为上面的更整洁。顾名思义,returning 子句将返回插入的元组。

BTW timestamp 是保留字,不应用作列名。

【讨论】:

  • +1 表示“unnest”并指出“时间戳”问题,这是使用 ORM 的残余。
  • (在 postgres 中,'timestamp' 似乎没有保留。postgresql.org/docs/9.3/static/sql-keywords-appendix.html)
  • 您不需要选择中的列名。这也可以:INSERT INTO my_table (col1, col2) SELECT * FROM unnest(%s) s(col1 integer, col2 text) RETURNING *;
猜你喜欢
  • 2022-01-01
  • 2011-12-29
  • 2017-02-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-06-10
相关资源
最近更新 更多