Cur*_*arn 2 python mysql database oursql
我试图将python脚本生成的一些数据存储在MySQL数据库中.基本上我使用的命令:
con = oursql.connect(user="user", host="host", passwd="passwd",
db="testdb")
c = con.cursor()
c.executemany(insertsimoutput, zippedsimoutput)
con.commit()
c.close()
Run Code Online (Sandbox Code Playgroud)
哪里,
insertsimoutput = '''insert into simoutput
(repnum,
timepd,
...) values (?, ?, ...?)'''
Run Code Online (Sandbox Code Playgroud)
插入大约30,000行,大约有15列.以上大约需要7分钟.如果我使用MySQLdb而不是我们的MySQL,大约需要2秒钟.为何如此巨大的差异?这应该是在myql中以其他方式完成的,我们的自己的mysql只是很慢吗?如果有更好的方法用oursql插入这些数据,如果你能告诉我,我将不胜感激.
谢谢.
区别在于MySQLdb对你的查询做了一些hackery,而我们的mysql没有......
考虑到这个:
cursor.executemany("INSERT INTO sometable VALUES (%s, %s, %s)",
[[1,2,3],[4,5,6],[7,8,9]])
Run Code Online (Sandbox Code Playgroud)
在运行之前,MySQLdb会对其进行翻译:
cursor.execute("INSERT INTO sometable VALUES (1,2,3),(4,5,6),(7,8,9)")
Run Code Online (Sandbox Code Playgroud)
但如果你这样做:
cursor.executemany("INSERT INTO sometable VALUES (?, ?, ?)",
[[1,2,3],[4,5,6],[7,8,9]])
Run Code Online (Sandbox Code Playgroud)
在oursql中,它被翻译成类似这样的伪代码:
stmt = prepare("INSERT INTO sometable VALUES (?, ?, ?)")
for params in [[1,2,3],[4,5,6],[7,8,9]]:
stmt.execute(*params)
Run Code Online (Sandbox Code Playgroud)
因此,如果你想模仿mysqldb正在做的事情,但是从预备语句和selfql的其他优点中受益,你需要这样做:
from itertools import chain
data = [[1,2,3],[4,5,6],[7,8,9]]
one_val = "({})".format(','.join("?" for i in data[0]))
vals_clause = ','.join(one_val for i in data)
cursor.execute("INSERT INTO sometable VALUES {}".format(vals_clause),
chain.from_iterable(data))
Run Code Online (Sandbox Code Playgroud)
我敢打赌,当你这样做时,我们的mysql会更快:-)
而且,如果你认为它丑陋,你是对的.但是请记住MySQL db在内部做了一些更糟糕的事情 - 它使用正则表达式来解析你的INSERT语句并中断参数化部分然后做我建议你为我们做的事情.