我以这种方式插入行,data
是多个fieldname: fieldvalue
项的字典:
def add_row(self, data, table): #data is a dictionary
columns = data.keys()
values = []
for column in columns:
if isinstance(data[column], list): #checking for json values
values.append(Json(data[column]))
elif isinstance(data[column], dict):
values.append(Json(data[column]))
else:
values.append(data[column])
insert_statement = 'insert into %s ' % table + '(%s) values %s'
self.cur.execute(insert_statement, (AsIs(','.join(columns)), tuple(values)))
self.conn.commit()
print "added %s" % table
但是现在我想批量插入行以提高性能并减少I / O使用。问题是我找不到正确的方法。以下函数抛出(data
是上述项目的列表):
psycopg2.ProgrammingError: syntax error at or near "[" LINE 1: ...,category_id,initial_quantity,base_price) VALUES ([u'Entrega...
def add_row_bulk(self, data, table): #data is a dictionary
columns = data[0].keys()
value_rows = []
for e in data:
columns = e.keys()
values = []
for column in columns:
if isinstance(e[column], list): #checking for json values
values.append(Json(e[column]))
elif isinstance(e[column], dict):
values.append(Json(e[column]))
else:
values.append(e[column])
value_rows.append(AsIs(values))
cols = (AsIs(','.join(columns)))
query = self.cur.mogrify("INSERT INTO item (%s) VALUES %s", (cols, tuple(value_rows)))
self.cur.execute(query)
self.conn.commit()
print "added %s" % table
答案 0 :(得分:2)
您的SQL生成代码存在一些问题。
首先,AsIs(values)
不会mogrify
进入值行,就像您似乎希望的那样。测试它,似乎等同于AsIs(str(values))
。这是你在抛出的错误中看到的输出。
在您的工作示例中有用的是在单独的值元组上使用mogrify
。将tuple(values)
添加到value_rows
,而不是AsIs(values)
。
其次,要指定在一个insert语句中插入多个行的值,您需要SQL syntax similar to the following:
... VALUES (1, 'x'), (2, 'y'), (3, 'z')
请注意,值列表列表周围没有(
)
。什么都没有(我知道),奇怪的是mogrify
进入这样的列表。当然tuple
不会。
所以你需要做一些事情:
self.cur.mogrify('INSERT INTO item (%s) VALUES %s,%s,%s,%s',
(cols, value_row1, value_row2, value_row3, value_row4))
这意味着你需要做更多的工作来生成mogrify
的两个参数,因为事先不知道行数。要生成第一个参数,您可以执行以下操作:
'INSERT INTO item (%s) VALUES ' + ','.join(['%s'] * len(value_rows))
第二个参数必须是第一个值为cols
的序列,其余为value_rows
的内容。一种方法:
[cols] + value_rows