【python下用sqlite3, 多线程下报错,原因和解决 】

在python下用sqlite3, 多线程 在UPDATE 或者INSERT的时候, 会报错

sqlite3.OperationalError: cannot commit - no transaction is active

1. 原因

多线程写冲突

  • 非原子写操作:如果多个线程同时执行非原子写操作,可能会导致数据覆盖或不一致。

2. 解决方案

使用锁

使用锁来确保同一时间只有一个线程可以执行写操作。

go 复制代码
import sqlite3
import threading

lock = threading.Lock()

def worker(conn, thread_id):
    with lock:
        cursor = conn.cursor()
        cursor.execute("INSERT INTO test (id, value) VALUES (?, ?)", (thread_id, f"value_{thread_id}"))
        conn.commit()
        cursor.close()

def main():
    conn = sqlite3.connect('example.db', check_same_thread=False)
    cursor = conn.cursor()
    cursor.execute("CREATE TABLE IF NOT EXISTS test (id INTEGER PRIMARY KEY, value TEXT)")
    conn.commit()
    cursor.close()

    threads = []
    for i in range(5):
        thread = threading.Thread(target=worker, args=(conn, i))
        threads.append(thread)
        thread.start()

    for thread in threads:
        thread.join()

    conn.close()

if __name__ == "__main__":
    main()

使用事务

显式事务管理:在每个线程中显式地开始和提交事务,确保事务的原子性和一致性。

go 复制代码
import sqlite3
import threading

def worker(conn, thread_id):
    cursor = conn.cursor()
    cursor.execute("BEGIN")
    cursor.execute("INSERT INTO test (id, value) VALUES (?, ?)", (thread_id, f"value_{thread_id}"))
    conn.commit()
    cursor.close()

def main():
    conn = sqlite3.connect('example.db', check_same_thread=False)
    cursor = conn.cursor()
    cursor.execute("CREATE TABLE IF NOT EXISTS test (id INTEGER PRIMARY KEY, value TEXT)")
    conn.commit()
    cursor.close()

    threads = []
    for i in range(5):
        thread = threading.Thread(target=worker, args=(conn, i))
        threads.append(thread)
        thread.start()

    for thread in threads:
        thread.join()

    conn.close()

if __name__ == "__main__":
    main()
相关推荐
一位代码24 分钟前
微软开源项目MarkitDown:一款将pdf/word/ppt等各类文件转换为Markdown格式的python工具
python
曹牧7 小时前
Oracle:前缀匹配之REGEXP_LIKE
数据库·oracle
Unbelievabletobe7 小时前
解决了股票api接口盘后数据更新慢的问题
大数据·开发语言·python
lpd_lt9 小时前
AI Coding的常用Prompt技巧
python·ai·ai编程
小江的记录本9 小时前
【JVM虚拟机】堆内存分代模型:年轻代(Eden+Survivor)、老年代、元空间Metaspace(附《思维导图》+《面试高频考点清单》)
java·前端·jvm·后端·python·spring·面试
在繁华处9 小时前
Java从零到熟练(三):流程控制
java·开发语言·python
asdzx679 小时前
使用 Python 快速提取 PDF 中的表格
python·pdf
无情的西瓜皮9 小时前
MCP协议实战:用Python从零搭建一个AI Agent工具服务器(保姆级教程)
服务器·人工智能·python·mcp
暴躁小师兄数据学院10 小时前
【AI大数据工程师特训笔记】第05讲:关联查询
数据库·sql·oracle
倔强的石头_10 小时前
《Kingbase护城河》——跨平台环境下的数据库联调实战
数据库