我在 PostgreSQL 工作,我刚刚开始学习同时工作的事务。 我的问题是当我运行整个脚本时,我得到了相同的事务 ID。 第一个元组应该有 1 个 id,第二个 2 应该有相同的 id。
当我逐行(逐行)运行脚本时,我得到了正确的结果。 为什么会这样?
DELETE FROM test;
INSERT INTO test VALUES (1, 'A');
BEGIN TRANSACTION;
INSERT INTO test VALUES (2, 'B');
INSERT INTO test VALUES (3, 'C');
COMMIT TRANSACTION;
最佳答案
该代码块在单个事务中执行。你还没有说它是如何执行的,但是如果你把它放在 pgadmin 中并一起运行,或者把它放在一个文件中并用 psql 调用它,事务将自动启动并在最后提交。 BEGIN TRANSACTION
行不会启动新事务,因为事务已经打开。这就是为什么一起执行它会创建具有相同事务 ID 的行。
为了演示,逐行运行:
BEGIN;
INSERT INTO test VALUES (1, 'A');
SELECT txid_current();
BEGIN TRANSACTION;
INSERT INTO test VALUES (2, 'B');
INSERT INTO test VALUES (3, 'C');
SELECT txid_current();
COMMIT TRANSACTION;
您会看到每个 SELECT
都返回相同的 ID。您还会在第二个 BEGIN
上看到一条消息,表明交易已经在进行中。
但是,如果您(在 pgadmin 中)仅突出显示第一个 INSERT
并执行它(无需手动执行 BEGIN
),那么这是该自动事务中唯一执行的行.然后其余部分在第二个事务中执行,无论您一次执行一行还是一起执行,因为事务是手动处理的。
现在,如果您同时运行这些行:
BEGIN;
INSERT INTO test VALUES (1, 'A');
COMMIT;
BEGIN;
INSERT INTO test VALUES (2, 'B');
INSERT INTO test VALUES (3, 'C');
COMMIT;
然后运行这个:
SELECT xmin, *
FROM test
您会看到交易编号符合预期,因为现在交易完全由手动控制 - 为第一个报表创建一个,为另外两个创建第二个。
关于sql - 请解释为什么脚本以这种方式工作,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56476813/