Python psycopg2检查行存在

时间:2013-12-08 02:11:00

标签: python sql postgresql psycopg2

在Python中psycopg2如何检查行是否存在?

def track_exists(self, track_id):
    cur = self.conn.cursor()
    cur.execute("SELECT fma_track_id FROM tracks WHERE fma_track_id = %s", (track_id,))
    if cur.fetchall() > 0:
        return true
    else:
        return false

目前我正在

Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "mumu.py", line 38, in track_exists
if cur.fetchall() > 0:
TypeError: 'NoneType' object has no attribute '__getitem__'

4 个答案:

答案 0 :(得分:22)

不要使用fetchall()(返回一个永远不会大于0的列表),使用fetchone()

def track_exists(self, track_id):
    cur = self.conn.cursor()
    cur.execute("SELECT fma_track_id FROM tracks WHERE fma_track_id = %s", (track_id,))
    return cur.fetchone() is not None
如果没有要获取的内容,

fetchone()会返回None,针对is not None的测试会为您提供一个方便的布尔值来直接返回。

答案 1 :(得分:10)

使用exists将允许Postgresql在第一次出现时停止搜索,而不是搜索直到用尽:

exists_query = '''
    select exists (
        select 1
        from tracks
        where fma_track_id = %s
    )'''
cursor.execute (exists_query, (track_id,))
return cursor.fetchone()[0]

另一个优点是它总是返回一个包含布尔值的行,可以直接使用而无需进一步解释。

答案 2 :(得分:2)

您可以使用rowcount轻松地处理它。这是psycopg文档中关于rowcount的内容,

此只读属性指定最后一次执行*()产生(对于SELECT等DQL语句)或受影响的(对于UPDATE或INSERT等DML语句)的行数。

如果在光标上没有执行execute*(),或者如果接口无法确定最后一次操作的行数,则该属性为-1。

因此,以下示例将使您更好地了解如何使用rowcount


示例-1

>> # if your SELECT query doesn't have any values you'll get 0 as the output
>>> query_1 = 'SELECT * FROM some_table LIMIT 0;'
>>> cursor.execute(query)
>>> cursor.rowcount
0

示例-2

>>> query_2 = 'SELECT * FROM some_table LIMIT 1;'
>>> cursor.execute(query)
>>> cursor.rowcount
1

示例-3

>>> # no LIMIT in the query, so you'll get the whole row count
>>> query_3 = 'SELECT * FROM some_table;'
>>> cursor.execute(query)
>>> cursor.rowcount
14000

示例-4

>>> # this query won't return anything, so you'll get -1 as the rowcount
>>> query_4 = 'CREATE TABLE new_table AS SELECT * FROM old_table;'
>>> cursor.execute(query)
>>> cursor.rowcount
-1

因此您可以按如下所示修改功能,

def track_exists(self, track_id):
    cur = self.conn.cursor()
    cur.execute("SELECT fma_track_id FROM tracks WHERE fma_track_id = %s", (track_id,))

    # if cur.rowcount > 0:
    #     return True
    # else:
    #     return False

    return cur.rowcount > 0  # more Pythonic way

请注意:如果执行UPDATE查询,您将获得rowcount的更新行数。因此,基本上rowcount将显示受查询影响的行数。 CREATE查询不会影响任何行,因此这就是为什么rowcount得到-1的原因。

答案 3 :(得分:-1)

await Task.WhenAll(task1, task2, task3, etc)