我正在创建一个临时表,并使用相同的命令和连接用两个单独的语句填充它。但是,如果我创建在创建之前插入参数的表,则会收到“无效的对象名称”。如果我在创建后添加它,它可以正常工作。
临时表应该持续整个会话,所以当参数添加到命令对象时,我看不出它的重要性。
失败:
using (SqlConnection conn = new SqlConnection("Data Source=.;Initial Catalog=TEST;Integrated Security=True;"))
using (SqlCommand cmd = conn.CreateCommand())
{
conn.Open();
cmd.Parameters.Add(new SqlParameter("@ID", 1234));
cmd.CommandText = "CREATE TABLE #Test (ID INT NOT NULL PRIMARY KEY, I INT NOT NULL)";
cmd.ExecuteNonQuery();
cmd.CommandText = "INSERT INTO #Test VALUES (@ID, 1)";
cmd.ExecuteNonQuery();
..... more code that uses the table
}
WORKS:
using (SqlConnection conn = new SqlConnection("Data Source=.;Initial Catalog=TEST;Integrated Security=True;"))
using (SqlCommand cmd = conn.CreateCommand())
{
conn.Open();
cmd.CommandText = "CREATE TABLE #Test (ID INT NOT NULL PRIMARY KEY, I INT NOT NULL)";
cmd.ExecuteNonQuery();
cmd.Parameters.Add(new SqlParameter("@ID", 1234));
cmd.CommandText = "INSERT INTO #Test VALUES (@ID, 1)";
cmd.ExecuteNonQuery();
..... more code that uses the table
}
修改
SQL Profiler对此有了更多了解。
如果命令有任何参数,则底层代码发出“exec sp_executesql”。如果清除了参数,则底层代码会发出更直接的“CREATE TABLE”。在sp_executesql之后清理临时表,这解释了我在这里看到的内容。
对我来说,这将是SqlCommand(或相关)代码中的一个错误,但由于我现在有一个解释,我可以继续。
答案 0 :(得分:7)
问题实际上是在" exec sp_executesql"声明。当ADO检测到sqlCommand中声明了参数时,默认使用" sp_executesql"而不是" exec"。但在这种情况下,第一个命令是创建TEMPORAL表,并且如已知的那样,临时表仅在存储过程(sp_executesql)内有效,并在退出时被删除。因此第二个INSERT语句在第一个示例代码中不再有效。在第二个中,临时表成功创建,并且insert语句正常执行。希望它有所帮助。
答案 1 :(得分:0)
我怀疑第一次执行的状态失败,因为它坚持必须使用每个参数。