0

I have this slice of code that works sometimes and sometimes not. The query that is being executed has not been written by myself, but I am told that all I have to do is run it against the database to get the results I need. Here is my code:

try {
  using (SqlDataReader dr = cmd.ExecuteReader()) {
    while (dr.Read()) {
      try {
        list.Add(dr.GetString(3) + " " + dr.GetInt32(4).ToString() + " " + dr.GetString(5) + " " + dr.GetDecimal(8).ToString());
      } catch (Exception e) {
        list.Add("fail");
      }
    }
  }
} catch (SqlException sqlException) {
  Debug.WriteLine(sqlException.Message);
}

The error that I sometimes receive is that I cannot drop a table because I do not have permission or the table does not exist. Other times the query executes without any problems and I am able to retrieve and store my results in a list.

When I run the query in SQL Server 2008, sometimes I do indeed get errors but the results still show up and are what I expect. So my question is: How can I grab these results regardless of the error that seems to come up whenever it feels like?

Here is a tiny piece of the query that is causing me my troubles:

IF  EXISTS (SELECT * from tempdb..sysobjects where name like '#TABLE%')  
DROP #TABLE

There are many of these if statements in the query that i am running and it's unpredictable which one is going to cause an error. So what i have done for right now is surround the DROP #TABLE in a try-catch block so that at least i can still get retrieve the results in my silverlight program. I will get with my higher up and ask him why the query is returning these errors spontaneously..

4

1 回答 1

1

编辑

没关系,我看到了问题。我忘记了临时表名称附加了其他字符以防止不同进程之间的命名冲突(例如#TABLE___...___0000000064E2)。

我的猜测是,在某些情况下,存储过程正在创建一个名为“#TABLE”的临时表,而您发布的那段 SQL 代码旨在执行清理。单独运行时,这可能工作正常。

当存储过程由多个客户端同时运行时,或者如果先前的查询之一以某种方式未能执行清理(可能是由于中途出现错误),问题可能开始出现。在这种情况下,会产生误报(存储过程认为清理是必要的,但它实际上看到的是另一个进程创建的临时表)。然后你会得到错误,因为没有与当前进程关联的#TABLE。

无论如何,将语句包装在 try-catch 中似乎是一种不错的方法。更好的方法是对代码进行彻底检查,可能设置某种标志以帮助指示清理是必要的,或者使用公用表和某种事务键(删除与当前事务关联的所有记录,而不是删除桌子)。

您可能还想考虑使用表变量而不是临时表。

请参阅:
http ://social.msdn.microsoft.com/Forums/en-US/sqltools/thread/02337dd5-5cfd-40d8-b529-12dc557d6a7e/

或者,您也可以考虑DROP完全跳过以下语句:
Temporary Table Scope?


为了回答您最初的问题,我不知道有任何方法可以从 SQL 查询中检索结果,一旦它引发异常,而不是通过 .NET 程序集。SQL Server Management Studio 使用一些重型、定制的 API,这些 API 可能不值得您学习和使用。


忽略以下
(留作参考)

如果可以,请尝试将 SQL 查询更改为

IF  EXISTS (SELECT * from tempdb..sysobjects where name = '#TABLE')
DROP #TABLE

like '#TABLE%'改为= '#TABLE'

like语句没有任何意义......是否有其他以“#TABLE”开头的表都没关系......您只想知道是否有一个完全命名为“#TABLE”的表。

我的猜测是,这是逻辑被改变的情况之一,但只是中途改变,可能是两个不同的人。

于 2012-12-28T19:30:00.090 回答