【问题标题】:Python and sqlite3.ProgrammingError: Recursive use of cursors not allowedPython 和 sqlite3.ProgrammingError:不允许递归使用游标
【发布时间】:2014-12-25 01:58:36
【问题描述】:

我写了一个这样的python程序,它应该在多线程模式下运行:

def Func(host,cursor,db):

    cursor.execute('''SELECT If_index, Username, Version, Community, Ip_traff FROM HOST WHERE
    Hostname = ?''',(host,))

    #do something

#--- Main ---

db = sqlite3.connect(os.getcwd()+'\HOST', check_same_thread = False) #opendatabase       
cursor = db.cursor()                                                 #generate a cursor

for ii in range(len(host)):  #host is a list of ipaddress

    #for each host i want generate a thread
    thr = threading.Thread(target = Func, args=(host[ii],cursor,db) 
    thr.start()

我收到 sqlite3.ProgrammingError: Recursive use of cursors not allowed。在这种情况下,如何管理 sqlite3 的递归游标? 多谢 保罗

【问题讨论】:

  • 你为什么不给每个线程自己的光标?

标签: python multithreading sqlite database-cursor


【解决方案1】:

好吧,问题是 sqlite3 模块不喜欢多线程情况,你可以在 sqlite3 模块的文档中看到这一点

...Python 模块不允许在线程之间共享连接和游标[1]

我要做的是在 Func 函数中使用某种同步,例如 threading.Lock[2]。您的 Func 将如下所示:

# Define the lock globally
lock = threading.Lock()

def Func(host,cursor,db):
    try:
        lock.acquire(True)
        res = cursor.execute('''...''',(host,))
        # do something
    finally:
        lock.release()

前面的代码会同步 cursor.execute 的执行,只让一个线程获取锁,其他线程将等待直到它被释放,当拥有锁的线程完成时,它会释放锁给其他线程拿去吧。

这应该可以解决问题。

[1]https://docs.python.org/2/library/sqlite3.html#multithreading

[2]https://docs.python.org/2/library/threading.html?highlight=threading#rlock-objects

【讨论】:

  • 我用过 lock: 而不是 try and finally(更紧凑)谢谢 :)
猜你喜欢
  • 1970-01-01
  • 2015-07-03
  • 1970-01-01
  • 2010-10-13
  • 2016-12-28
  • 1970-01-01
  • 2012-09-25
  • 2021-08-20
  • 1970-01-01
相关资源
最近更新 更多