2012-04-03 81 views
0

我在我的应用程序中使用MS Sql数据库,当我从数据库执行SELECT操作时,它会搜索几分钟。 它每天发生几次。所有其他SELECTS只需几秒钟。数据库卡在SELECT操作

另外我注意到,如果我在SELECT操作正在进行时关闭应用程序。直到我重新启动数据库引擎时,它根本无法工作...

为什么会这样?

这里是代码片段:

 using (SqlConnection myConnection = new SqlConnection(connString)) 
     { 
      myConnection.Open(); 

      SqlCommand command = myConnection.CreateCommand(); 
      SqlTransaction transaction; 

      transaction = myConnection.BeginTransaction("LockTransaction"); 

      command.Connection = myConnection; 
      command.Transaction = transaction; 

      try 
      { 
       int recordsAtOnce = maxToLock; 
       command.CommandText = 
       "SELECT TOP 1000 id, productName from Parts WHERE part_used is NULL;"; 

       List<string> idList = new List<string>(); 
       SqlDataReader myReader = command.ExecuteReader(CommandBehavior.Default); 
       while (myReader.Read()) 
       { 
        string id = myReader.GetString(1); 
        string name = myReader.GetInt32(0).ToString(); 
        idList.Add(id); 
       } 

       myReader.Close(); 

       string idsStr = ""; 
       for(int i = 0; i < idList.Count; i++) 
       { 
        if (i != 0) 
        { 
         idsStr += ", "; 
        } 

        idsStr += idList[i]; 
       } 

       // lock record 
       command.CommandText = "UPDATE Parts SET part_used=\'rt\' WHERE id in (" + idsStr + ")"; 
       command.Parameters.Clear(); 
       command.CommandType = CommandType.Text; 

       command.ExecuteNonQuery(); 

       transaction.Commit();      
      } 
      catch (Exception ex) 
      { 
       transaction.Rollback();      
      } 
+0

'part_used'是你的'Parts'表的索引吗?这将避免表扫描。在不指定ORDER的情况下,有一个“TOP”子句是不寻常的。 – HABO 2012-04-03 15:17:09

回答

3

我觉得你的读者值被分配到了错误的变量。

尝试改变:

string id = myReader.GetString(1); 
string name = myReader.GetInt32(0).ToString(); 
idList.Add(id); 

要:

string id = myReader.GetInt32(0); 
string name = myReader.GetString(1).ToString(); 
idList.Add(id); 
2

这是最有可能,因为锁。如果另一个事务正在写入Parts表中,则您的选择需要等待。

0

零件表有多大?这可能会导致性能问题。或者它可能是另一个在你面前锁定的交易。

其他的事情:当通过使用

  • 参数化第二次查询,而不是字符串concating与他们做了你的连接,命令和读者

    • 调用Dispose。由于Sql Server的内部工作原理,它更安全,性能更高。

    • minor:如果您正在查看数千个项目,请使用StringBuilder而不是连接。