16

如果我想在不同的表上运行多个 SELECT 查询,我可以对所有表使用相同的 SqlDataReader 和 SqlConnection 吗?以下是明智的吗?(我输入得很快,所以它缺少 try/catch):

MySqlCommand myCommand = new MySqlCommand("SELECT * FROM table1", myConnection);

myConnection.Open();
SqlDataReader myDataReader = myCommand.ExecuteReader();

while(myReader.Read())
{
    //Perform work.
}

myCommand.commandText = "SELECT * FROM table2";

myReader = myCommand.ExecuteReader();

while(myReader.Read())
{
    //Perform more work
}

myReader.Close();
myConnection.Close();

非常感谢。

4

2 回答 2

28

您可以对它们中的每一个使用相同的连接,只要您不尝试在来自不同线程的同一连接上同时执行多个查询。

至于数据阅读器,您实际上并没有重用阅读器,每次调用都ExecuteReader返回一个新阅读器的新实例,您重用的只是维护对阅读器的引用的变量。这里存在一个问题,您只是显式地关闭最后一个阅读器,并让第一个阅读器在以后的某个时间进行 GC。

您也可以重用命令,但请记住,如果您提供参数等,您将需要为下一个查询清除它们,除非它们也适用于下一个查询。

您应该使用try/finally块来确保清理资源,或者在这里快速更改代码以使用using语句来确保资源清理,即使存在阻止其余代码执行的异常也是如此。

using (var myConnection = GetTheConnection())
{
  myConnection.Open();

  var myCommand = new MySqlCommand("SELECT * FROM table1", myConnection))
  using (var myDataReader = myCommand.ExecuteReader())
  {
    while(myReader.Read())
    {
      //Perform work.
    }
  } // Reader will be Disposed/Closed here

  myCommand.commandText = "SELECT * FROM table2";
  using (var myReader = myCommand.ExecuteReader())
  {
    while(myReader.Read())
    {
      //Perform more work
    }
  } // Reader will be Disposed/Closed here
} // Connection will be Disposed/Closed here

注意:GetTheConnection对于您用来获取连接实例的任何机制,它只是一个占位符功能。

于 2012-04-13T19:22:26.037 回答
2

我通常使用适配器,所以我对读者的细节生疏,但我认为你走在正确的轨道上。

您的代码中需要注意的一点是,每次调用都ExecuteReader应该生成一个新的数据读取器。您可能正在重用变量名称,但对现有阅读器的引用将被丢弃,并在每次调用时被新的阅读器替换。重点是,在使用 ExecuteReader 获取新阅读器之前关闭前一个阅读器。

于 2012-04-13T19:29:03.197 回答