如何在C#中多次执行存储过程

时间:2011-09-13 00:07:38

标签: c# procedures

我有一个时间表应用,用户可以在一周中的不同日期输入/输出他们的时间。表单处理每天的输入/输出,将它们作为参数填充到存储过程中并将它们添加到数据库中。我怎样才能最有效地完成这项工作?我无法访问数据库,只能访问存储过程。

这是背后的代码,我已经删除了一些不必要的代码。

SqlConnection conn = new SqlConnection(connString);
conn.Open();
SqlCommand cmd = new SqlCommand("insertINOUT", conn);
cmd.CommandType = CommandType.StoredProcedure;

cmd.Parameters.Add(new SqlParameter("@UserName", user));

for (int j = 0; j < weekDays.Length; j++)
{
    cmd.Parameters.Add(new SqlParameter("@In", in));
    cmd.Parameters.Add(new SqlParameter("@Out", out));
    cmd.ExecuteReader();
}
conn.Close();

如果只有1天的进/出,代码可以正常工作。如果用户填写多天,我将收到此错误:参数'@In'已多次提供。

感谢您的帮助。

6 个答案:

答案 0 :(得分:16)

SqlConnection conn = new SqlConnection(connString);
conn.Open();
SqlCommand cmd = new SqlCommand("insertINOUT", conn);
cmd.CommandType = CommandType.StoredProcedure;

for (int j = 0; j < weekDays.Length; j++)
{
    **cmd.Parameters.Clear();**
    cmd.Parameters.Add(new SqlParameter("@UserName", user));
    cmd.Parameters.Add(new SqlParameter("@In", in));
    cmd.Parameters.Add(new SqlParameter("@Out", out));
    cmd.ExecuteReader();
}
conn.Close();

(您必须在每次迭代时清除参数。)

答案 1 :(得分:1)

另一种方法是,您可以更改SqlCommand的范围,以便每次都重新创建它。

SqlConnection conn = new SqlConnection(connString);
conn.Open();

for (int j = 0; j < weekDays.Length; j++)
{
    SqlCommand cmd = new SqlCommand("insertINOUT", conn);
    cmd.CommandType = CommandType.StoredProcedure;

    cmd.Parameters.Add(new SqlParameter("@UserName", user));
    cmd.Parameters.Add(new SqlParameter("@In", in));
    cmd.Parameters.Add(new SqlParameter("@Out", out));
    cmd.ExecuteReader();
}
conn.Close();

似乎有点浪费,但有一些库以这种方式工作(想到企业库DAAB)。

答案 2 :(得分:1)

using (SqlConnection conn ... )
{
    SqlCommand cmd = ...
    ...
    // Set up the parameter list.
    //   You can use   .AddWithValue   here to add values that don't change in the loop.
    cmd.Parameters.Add("@Username", SqlDbType.VarChar);
    ...
    for (...)
    {
        // Load one set of loopy values.
        cmd.Parameters["@UserId"].Value = user;
        ...
    }
}

答案 3 :(得分:1)

这是因为您试图将相同的参数重新添加到相同的 sqlcommand 对象中。为了获得最佳性能,在开始 for 循环之前,打开连接并添加不带值的参数。然后,在您的 for 循环中,您所做的就是设置参数的值,然后执行该过程。无需在循环的每次迭代中自行重新创建参数,您只是在白白地消耗资源。试试这个:

string strCon = "Your Connection String Here";
using (SqlConnection conSQL = new SqlConnection(strCon))
{
    conSQL.Open();
    using (SqlCommand cmdSQL = new SqlCommand())
    {
        cmdSQL.CommandType = CommandType.StoredProcedure;
        cmdSQL.CommandText = "The Name of Your Stored Procedure Here";
        cmdSQL.Connection = conSQL;
        // I'm just going to assume that the data type for the
        // parameters is nvarchar and that both are input parameters...
        // Just for demonstration purposes
        cmdSQL.Parameters.Add("@In", SqlDbType.NVarChar, 50);
        cmdSQL.Parameters.Add("@Out", SqlDbType.NVarChar, 50);
        for (var j = 0; j <= weekDays.Length - 1; j += 1)
        {
            cmdSQL.Parameters("@In").Value = strIn;
            cmdSQL.Parameters("@Out").Value = strOut;
            // I'm not sure why in your code you put ExecuteReader here.
            // You don't show that you're using the reader at all, rather
            // it looks like you are actually just trying to execute the procedure without
            // using any type of return parameter values or a reader.
            // So I changed the code here to be what it should be if that is true.
            cmdSQL.ExecuteNonQuery();
        }
    }
    conSQL.Close();
}

我知道这个问题已经过去好几年了,但我想仍然会有人搜索这个,也许会发现这个答案有帮助。

答案 4 :(得分:0)

您收到该错误的原因是因为for循环多次重新添加参数:

cmd.Parameters.Add(new SqlParameter("@In", in));
cmd.Parameters.Add(new SqlParameter("@Out", out));

执行此操作的正确方法是清除foor循环最后一行的Parameters集合,或者只是检查参数是否已存在并设置其值而不是执行Parameters.Add

答案 5 :(得分:0)

SqlConnection conn = new SqlConnection(connString);
conn.Open();
SqlCommand cmd = new SqlCommand("insertINOUT", conn);

    cmd.CommandType = CommandType.StoredProcedure;
    cmd.Parameters.Add(new SqlParameter("@UserName", user));
    for (int j = 0; j < weekDays.Length; j++)
    {


        cmd.Parameters.Add(new SqlParameter("@In"+j, in));
        cmd.Parameters.Add(new SqlParameter("@Out"+j, out));
        cmd.ExecuteReader();
    }
    conn.Close();