MySQL 中的多个同时 SELECT 语句

Posted

技术标签:

【中文标题】MySQL 中的多个同时 SELECT 语句【英文标题】:Multiple simultaneous SELECT statements in MySQL 【发布时间】:2013-09-09 08:26:24 【问题描述】:

我正在尝试获取 mysql 数据库中两次更改内容的快照。我有许多不同实体的表,每个表都有一个“上次更新”列,当一行更新时,该列会自动设置为当前日期。

我有一个客户端应用程序,它使用多个 SELECT 语句(数据库中的每个表一个)查询数据库,对于具有以下内容的任何行:“应用程序的先前同步时间”

Client App              |            Server App
SELECT * FROM Table1    |
                        |       Update Table1 & Table2, altering relationships
SELECT * FROM Table2    |

以便在获取快照的过程中修改表(和关系),可能会返回一些无效的关系信息(例如,服务器应用程序将新行插入表 1 和表 2,因此当客户端查询表 2 时,有引用表 1 中不存在的条目的行)。

我认为我需要使用事务或锁定,但我不确定哪个或是否有更好的方法。我正在使用 MySQL 连接器/.NET 从 C# 访问服务器。目前,我创建了一个 MySQLCommand,其中包含所有 SELECT 语句,例如:

string commandString = "SELECT * FROM Table1; SELECT * FROM Table2;";
using (MySqlCommand command = new MySqlCommand(commandString, connection))

然后阅读它们:

 using (MySqlDataReader reader = command.ExecuteReader())
 
     do
     
        if (reader.HasRows)
        
             //....
                 
      while (reader.NextResult());
 

如何防止在 SELECT 语句之间修改表?

【问题讨论】:

你试过LOCK和UNLOCK TABLES dev.mysql.com/doc/refman/5.0/en/lock-tables.html 那么我会做类似的事情:LOCK TABLES Table1 READ, Table2 READ;从表 1 中选择 *;从表 2 中选择 *;解锁表; ?这会阻止从其他连接写入这些表吗?如果有人在它被锁定时试图写会发生什么?它只是等待还是导致错误? 会产生锁错误。您可能希望先在测试环境中执行此操作,然后在实际运行之前进行备份。无论您做什么 1) 先备份 2) 尽可能测试环境。 表锁只保护其他会话不适当的读取或写入。持有锁的会话,即使是读锁,也可以执行表级操作,例如 DROP TABLE。截断操作不是事务安全的,因此如果会话在活动事务期间或持有表锁时尝试执行截断操作,则会发生错误。 【参考方案1】:

你应该使用事务。不在客户端应用上,而是在服务器应用上。

begin transaction
update table1 set ....
update table2 set ....
update table2 set ....
commit

这样,table1 和 table2 同时提交,确保客户端应用读取的一致性。

注意:您必须使用 InnoDB 引擎进行事务处理

【讨论】:

以上是关于MySQL 中的多个同时 SELECT 语句的主要内容,如果未能解决你的问题,请参考以下文章

Mysql | 总结 | 常用的查询语句(单表查询)

mysql UNION语句

mysql语句的简化:from中的临时表作为where中的条件

mysql的查询语句union是啥意思

mysql中insert与select的嵌套使用解决组合字段插入问题

MySql语句中Union和join的用法