如何在read_sql中传递元组'其中in' pandas中的子句python

时间:2017-09-04 14:45:32

标签: python sql oracle pandas

我将一个元组转换为read_sql方法中的字符串

sql = "select * from table1 where col1 in " + str(tuple1) + " and col2 in " + str(tuple2)

df = pd.read_sql(sql, conn)

这样工作正常但是,当元组只有一个值sql失败时,ORA-00936:缺少表达式,因为单个元素元组有一个额外的逗号

例如

tuple1 = (4011,)
tuple2 = (23,24)

形成的sql为

select * from table1 where col1 in (4011,) + " and col2 in (23,24)
                                        ^
ORA-00936: missing expression

除了使用字符串操作删除逗号之外,还有更好的方法吗?

是否有更好的方法来对read_sql函数进行paramatrize?

3 个答案:

答案 0 :(得分:3)

可能有更好的方法,但我会在查询时添加if语句,并使用.format()代替+来参数化查询。

可能的if语句:

if len(tuple1) < 2:
    tuple1 = tuple1[0]

这将根据您的输入而有所不同。如果你有一个元组列表,你可以这样做:

tuples = [(4011,), (23, 24)]
new_t = []
for t in tuples:
    if len(t) == 2:
         new_t.append(t)
    elif len(t) == 1:
         new_t.append(t[0])

输出继电器:

[4011, (23, 24)]

使用.format()参数化查询的更好方法:

sql = "select * from table1 where col1 in {} and col2 in {}".format(str(tuple1), str(tuple2))

希望这有帮助!

答案 1 :(得分:3)

您收到错误的原因是SQL语法。

当您有WHERE col in (...)列表时,尾随逗号会导致语法错误。

无论哪种方式,使用字符串连接将值放入SQL语句都是不受欢迎的,并且最终会引发更多问题。

大多数Python SQL库都允许参数化查询。在不知道您使用哪个库进行连接的情况下,我无法链接确切的文档,但psycopg2的原理是相同的:

http://initd.org/psycopg/docs/usage.html#passing-parameters-to-sql-queries

此功能也在pd.read_sql中公开,因此为了实现您想要的安全,您可以这样做:

sql = "select * from table1 where col1 in %s and col2 in %s"

df = pd.read_sql(sql, conn, params = [tuple1, tuple2])

答案 2 :(得分:0)

select * from table_name where 1=1 and (column_a, column_b) not in ((28,1),(25,1))