Python MyQLdb执行将不接受参数

时间:2018-06-22 16:42:08

标签: python mysql

我发现了几个类似的问题,但似乎都无法解释这里发生的情况。

代码:

print type(price)
print type(sale_price)
print type(url)
price=0.0
sale_price=0.0
url="asdf"
dbc.execute("UPDATE logTable SET price=%f, salePrice=%f, modified=NOW() WHERE url=%s", [price, sale_price, url])

输出:

<type 'float'>
<type 'float'>
<type 'str'>
Traceback (most recent call last):
  File "./scrape.py", line 102, in <module>
    dbc.execute("UPDATE logTable SET price=%f, salePrice=%f, modified=NOW() WHERE url=%s", [price, sale_price, url])
  File "/usr/lib/python2.7/dist-packages/MySQLdb/cursors.py", line 210, in execute
    query = query % args
TypeError: float argument required, not str

插值字符串中没有杂散的%字符。参数的数量与占位符的数量匹配。类型肯定正确。

我尝试使用?占位符,而不是printf样式的占位符,即使文档建议两者都支持。这给出了一个不同的例外:

Traceback (most recent call last):
  File "./scrape.py", line 102, in <module>
    dbc.execute("UPDATE logTable SET price=?, salePrice=?, modified=NOW() WHERE url=?", [price, sale_price, url])
  File "/usr/lib/python2.7/dist-packages/MySQLdb/cursors.py", line 210, in execute
    query = query % args
TypeError: not all arguments converted during string formatting

该异常还会产生大量的StackOverflow答案,但没有一个真正揭示出这里出了什么问题。我确实尝试使用元组而不是列表作为第二个参数来使用两个样式占位符执行,但是仍然会得到相同的异常。

1 个答案:

答案 0 :(得分:1)

您的问题似乎表明这里有什么问题。事实并非如此。

根据Python数据库规范,具体的数据库库可以自由使用几个占位符之一作为(真实或伪)准备好的语句的参数。通常,选择是根据解决任务的最简单方法来完成的。

使用实际预准备语句的库可以使用?占位符。这使他们可以将语句直接传递到接口的预备语句引擎,因为它们通常使用?来放置要查询的数据。

其他库,例如MySQLdb,不使用准备好的语句,而是使用另一种(或多或少)安全的方法来创建查询。将数据嵌入到语句中。在这种情况下,可以使用%s(仅%s,不能使用其他模式)。在这些情况下,库会将给定的数据转换为适当的替换:用'字符括起字符串,并对内容进行适当处理,就像C函数mysql_real_escape_string()那样。其他数据的转换方式也不同,例如将数字转换为各自的字符串表示形式。

在所有情况下,都是根据这些数据创建字符串,然后将其插入查询中。这就是为什么使用%s而不使用其他内容(例如%f%d等)的原因。