在不同的命令中创建和填充临时表

时间:2016-06-21 21:05:32

标签: c# sql-server

我遇到了一个问题,我在一个#muMapping中创建了一个临时表SqlCommand,并用另一个SqlCommand填充它。第二个命令在cmd.ExecutNonQuery()上抛出异常并显示消息:

Invalid object name '#muMapping'.
Statement(s) could not be prepared.

两个命令都使用相同的SqlConnection,我开始并指定要使用的事务,以便SqlCommand不会隐式地开始和提交事务。

代码:

using (var conn = new SqlConnection(connString))
{
    await OpenConnection(conn);
    var trans = conn.BeginTransaction();

    using (SqlCommand cmd = conn.CreateCommand())
    {
        cmd.CommandText = "CREATE TABLE #muMapping ( mu_id INT NOT NULL PRIMARY KEY, facility NVARCHAR(100) NOT NULL, team NVARCHAR(100) NOT NULL );";
        cmd.Transaction = trans;

        await cmd.ExecuteNonQueryAsync();
    }

    using (SqlCommand cmd = conn.CreateCommand())
    {
        cmd.CommandText = "INSERT INTO #muMapping VALUES (@mu, @facility, @team);";
        cmd.Parameters.Add("@mu", SqlDbType.Int);
        cmd.Parameters.Add("@facility", SqlDbType.NVarChar, 100);
        cmd.Parameters.Add("@team", SqlDbType.NVarChar, 100);
        cmd.Transaction = trans;

        cmd.Prepare();

        foreach (var mu in loadData)
        {
            try
            {
                cmd.Parameters[0].Value = mu.Mu;
                cmd.Parameters[1].Value = mu.Facility;
                cmd.Parameters[2].Value = mu.Team;
                await cmd.ExecuteNonQueryAsync(); //Error thrown here
            }
            catch (Exception e)
            {
                Console.WriteLine(e.Message);
                throw e;
            }
        }
    }
    //Other statements
}

从我所看到的情况来看,#muMapping表应该从第二个命令可见。

2 个答案:

答案 0 :(得分:3)

来自Create Table

  

您可以创建本地和全局临时表。当地临时   表只在当前会话和全局临时中可见   表对所有会话都可见。临时表不能   分配。

因此,创建一个全局临时表(## table_name)

<强>更新

忽略我之前的陈述,我在sql server 2014上再次运行你的代码(经过极少的修改)并执行得很好!

public static void Bar()
    {

        Task.Run(async () =>
        {

            using (var conn = new SqlConnection("Server=.;Database=Test;Trusted_Connection=True;"))
            {
                await conn.OpenAsync();
                var trans = conn.BeginTransaction();

                using (SqlCommand cmd = conn.CreateCommand())
                {
                    cmd.CommandText =
                        "CREATE TABLE #muMapping ( mu_id INT NOT NULL PRIMARY KEY, facility NVARCHAR(100) NOT NULL, team NVARCHAR(100) NOT NULL );";
                    cmd.Transaction = trans;

                    await cmd.ExecuteNonQueryAsync();
                }

                using (SqlCommand cmd = conn.CreateCommand())
                {
                    cmd.CommandText = "INSERT INTO #muMapping VALUES (@mu, @facility, @team);";
                    cmd.Parameters.Add("@mu", SqlDbType.Int);
                    cmd.Parameters.Add("@facility", SqlDbType.NVarChar, 100);
                    cmd.Parameters.Add("@team", SqlDbType.NVarChar, 100);
                    cmd.Transaction = trans;

                    cmd.Prepare();


                    foreach (var i in new[] {1, 2, 3})
                    {
                        try
                        {
                            cmd.Parameters[0].Value = i;
                            cmd.Parameters[1].Value = "f";
                            cmd.Parameters[2].Value = "t";
                            cmd.ExecuteNonQuery(); //Error thrown here
                        }
                        catch (Exception e)
                        {
                            Console.WriteLine(e.Message);
                            throw;
                        }

                    }
                }
            }
        }).Wait();

        //Other statements
    }

看起来您可能有语法错误: Statement(s) Could Not Be Prepared. (SQL Error 37000)

答案 1 :(得分:0)

using (SqlConnection cn = new SqlConnection(GetConnectionString()))
{
cn.Open();


SqlTransaction transaction = cn.BeginTransaction();


SqlCommand cmd = new SqlCommand("create table #temp (colX int, colY int)", cn, 
transaction);
cmd.ExecuteNonQuery();


cmd = new SqlCommand("insert #temp values (10, 200)", cn, transaction);
cmd.ExecuteNonQuery();


cmd = new SqlCommand("select * from #temp", cn, transaction);
DataTable table = new DataTable();
table.Load(cmd.ExecuteReader());


transaction.Commit();
}