Php 有没有比交易更有效的方法?
上述操作将某些内容插入Php 有没有比交易更有效的方法?,php,mysql,transactions,Php,Mysql,Transactions,上述操作将某些内容插入表1,如果成功,则更新表2的计数字段 当然,这类事情可以由事务处理,但是事务需要锁定表,这在高并发系统中是没有效率的。如果您需要在该事务中更新多个表,情况可能会更糟 你的解决方案是什么 我使用的是PHP,我通过以下方式实现事务: insert into table1 ...; update table2 set count=count+1; 所以看起来那些$statement中引用的所有表都将被锁定?在我看来,这些表更像是一个“触发器”作业。onInsert执行某些操作。
表1
,如果成功,则更新表2
的计数
字段
当然,这类事情可以由事务处理,但是事务需要锁定表,这在高并发系统中是没有效率的。如果您需要在该事务中更新多个表,情况可能会更糟
你的解决方案是什么
我使用的是PHP,我通过以下方式实现事务:
insert into table1 ...;
update table2 set count=count+1;
所以看起来那些$statement
中引用的所有表都将被锁定?在我看来,这些表更像是一个“触发器”作业。onInsert执行某些操作。事务(在MySQL
上下文中假定InnoDB
)不需要锁定整个表
INSERT
将在不使用间隙锁的情况下锁定单个行
如果在WHERE
子句中的索引字段上提供相等或IN
条件,则UPDATE
也不会锁定任何间隙
这意味着,对于索引正确的表,插入项
不会相互阻止,而更新项
只会在它们影响同一行时相互阻止
UPDATE
当然会锁定它影响的单个行,但由于它是事务中的最后一个操作,因此在提交操作后会立即解除锁定
实际上,需要锁定本身,以便两个并发更新将按顺序增加计数。使用InnoDB存储引擎。它是行级锁定,而不是MyISAM,后者是表级锁定。事务对于确保“要么全有,要么全无”的行为非常重要——即使系统中存在高负载或高并发性,您也不应该停止使用事务,至少在您需要数据保持一致的情况下是如此
(并且事务不一定会锁定整个表)事务不一定会请求锁定整个表 此外,InnoDB使用不同的锁定策略支持不同的翻译隔离级别。您可能需要检查:
正如其他人指出的,使用支持行级锁定的数据库和简单地使用显式(或通过触发器隐式)事务可能更容易。它肯定更准确、更安全。或者您可以切换到Oracle,它(在大多数情况下)不执行锁定。:)
@LBushkin
:在Oracle
中对永久表执行的任何DML
操作都会锁定受影响的行,直到事务结束。Oracle将在相关的位置锁定行-这是获得正确事务行为所必需的。哪个版本的MySQL实现了稳定的触发器?插入操作可能不会相互阻塞行锁,但它们仍然可以与表中索引上的锁竞争,实际上,它们之间会发生死锁。我已经看过了。@MarkR
:你是对的,这就是为什么我特别提到“正确索引的表”。这里有一个关于你正在谈论的问题的问题:
mysql_query('begin');
mysql_query($statement1);
mysql_query($statement2);
...
mysql_query('commit');