MySQL MyISAM如何在不锁定表的情况下执行读取?

MySQL MyISAM如何在不锁定表的情况下执行读取?,mysql,sql,myisam,Mysql,Sql,Myisam,我的问题是我想了解如何在不使用MyISAM引擎锁定表的情况下执行select语句的后续问题 如果您有InnoDB但没有MyISAM,则答案如下。MyISAM引擎的等效物是什么 SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED ; SELECT * FROM TABLE_NAME ; COMMIT ; 这是MyISAM表的默认行为。如果要锁定MyISAM表,必须手动获取表级锁。事务隔离级别,启动事务,提交,回滚对MyISAM表的行为没有影响 更多关

我的问题是我想了解如何在不使用MyISAM引擎锁定表的情况下执行select语句的后续问题

如果您有InnoDB但没有MyISAM,则答案如下。MyISAM引擎的等效物是什么

SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED ;
SELECT * FROM TABLE_NAME ;
COMMIT ;

这是MyISAM表的默认行为。如果要锁定MyISAM表,必须手动获取表级锁。事务隔离级别,
启动事务
提交
回滚
对MyISAM表的行为没有影响

更多关于内部锁定机制的信息

读锁在执行
SELECT
语句之前隐式获取,在执行之后释放。请注意,可能同时运行多个并发的
SELECT
语句,因为多个会话可能在同一个表上持有读锁

相反,在执行
INSERT
UPDATE
DELETE
语句之前,会隐式获取写锁。这意味着,只要正在进行写入,就不会发生读取(更不用说并发写入了)*

以上内容仅适用于MyISAM、内存和合并表

您可能想在此处阅读更多有关此的信息:


*但是,由于以下原因,并不总是需要这些锁:

<> > <代码> MyISAM < /代码>存储引擎支持并行插入,以减少给定表中的读者和作者之间的争用:如果<代码> MyISAM < /C> >表在数据文件的中间没有空闲块,则总是在数据文件的末尾插入行。在这种情况下,您可以为一个不带锁的
MyISAM
表自由混合并发
INSERT
SELECT
语句


MyISAM确实在
SELECT
期间使用了读锁。在表格末尾插入一个
INSERT
,可以解决这个问题

但在长时间运行的
选择过程中,尝试执行
更新
删除
更改表
。反之亦然,在运行对表的更改时从表中读取。先到先发球,后一个线程阻塞,直到第一个线程完成

MyISAM不支持任何事务,因此它必须以这种方式工作。如果一个
SELECT
正在从表中读取行,并且一个并发线程更改了其中的一些行,那么您将得到一个竞争条件。
SELECT
可能会读取更改前的一些行和更改后的一些行,从而导致数据视图完全混淆

您使用
设置事务隔离级别所做的任何操作对MyISAM都没有影响


出于这些原因,建议改用InnoDB。

您能澄清一下“超出执行范围”吗?按照你所说的方式,这意味着whlie
SELECT
正在“执行”,表被锁定了……嗯,我几乎完全重写了我的答案。。。它应该读到“A
SELECT
永远不会在MyISAM表执行结束后锁定它”,但我希望新的措辞不那么晦涩。因此,在SELECT运行时,MyISAM仍然保持读取锁定。如果它是一个复杂的聚合选择,则同时会阻止所有其他插入。你不能禁用这个锁-OP实际上问的是什么。那么为什么说“这是MyISAM表的默认行为”。看起来更像是“这在MyISAM表中是不可能的”。我相信这个问题是从事务的角度提出的。据我所知,从他/她链接到的问题来看,@dev.e.loper希望通过MyISAM获得与他/她的代码片段相同的行为。他/她可能想澄清一下。我的回答是为了回答这个问题(即默认情况下,MyISAM的行为就像InnoDB一样,具有“读取未提交”隔离级别)顺便说一句,“MyISAM在select运行时仍保持读取锁定”并非完全正确(例如,仍然可以插入到表中,其中并发
select*,SLEEP(10)
正在运行)。我将重新措辞。