You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

SQLite中隐式事务的形态及多语句事务边界疑问

SQLite中隐式事务的形态及多语句事务边界疑问

嘿,这个问题问到点子上了!咱们来把SQLite的隐式事务逻辑讲明白~

首先得明确SQLite的默认行为:它默认处于自动提交(autocommit)模式。在这个模式下,规则是这样的:

  • 所有的写操作语句(比如INSERT、UPDATE、DELETE、CREATE TABLE这类)会自动被包裹在一个隐式事务里:执行语句前自动BEGIN TRANSACTION,语句执行成功后立刻自动COMMIT。
  • 而只读的SELECT语句,在自动提交模式下不会触发任何隐式事务——它就是直接执行查询,不需要事务的包裹。

那回到你的代码:

INSERT INTO artists(Name)
VALUE("Artist1"); -- 这里小提醒:SQLite里应该用VALUES,不是VALUE哦,不然会报错

SELECT *
FROM artists;

咱们来对应你的两种猜测分析:

  1. 第一种猜测(两个独立事务):

    BEGIN TRANSACTION;
    INSERT INTO artists(Name)
    VALUE("Artist1");
    COMMIT;
    
    BEGIN TRANSACTION;
    SELECT *
    FROM artists;
    COMMIT;
    

    这个是不准确的——因为SELECT语句不会触发隐式事务,所以第二个BEGIN TRANSACTION和COMMIT根本不会出现,SELECT就是直接执行的。

  2. 第二种猜测(一个事务包裹两个语句):

    BEGIN TRANSACTION;
    INSERT INTO artists(Name)
    VALUE("Artist1");
    SELECT *
    FROM artists;
    COMMIT;
    

    这个也不对,因为在默认自动提交模式下,INSERT执行完成后会立刻自动COMMIT,不会等后面的SELECT语句。所以两个语句不会被放在同一个隐式事务里。

如果想要让INSERT和SELECT处于同一个事务中,你需要显式开启事务,比如这样写:

BEGIN TRANSACTION;
INSERT INTO artists(Name) VALUES("Artist1");
SELECT * FROM artists;
COMMIT;

这时候两个语句会在同一个事务里执行,SELECT能读到INSERT刚插入的数据(事务内的一致性读取)。

总结一下:默认自动提交模式下,你的INSERT会单独触发一个隐式事务(执行后自动提交),SELECT直接执行无事务包裹;只有显式用BEGIN/COMMIT包裹多个语句时,它们才会属于同一个事务。

备注:内容来源于stack exchange,提问作者VanechikSpace

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.20 07:14:33