C#调用SQL Server中有参数的存储过程

 

一、使用SqlParameter的方式

代码:

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Data.SqlClient;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Configuration;
using System.Collections.ObjectModel;
using System.Reflection;

namespace ExecuteProcBySQLServer
{
  public partial class Form1 : Form
  {
      public Form1()
      {
          InitializeComponent();
      }

      private void btn_LoadData_Click(object sender, EventArgs e)
      {
          // 存储过程名称
          string strProcName = "usp_yngr_getInfectionCard_test";

          //定义存储过程的参数数组
          SqlParameter[] paraValues = {
                                      new SqlParameter("@BeginTime",SqlDbType.VarChar),
                                      new SqlParameter("@EndTime",SqlDbType.VarChar),
                                      new SqlParameter("@DateType",SqlDbType.Int),
                                      new SqlParameter("@PtName",SqlDbType.VarChar),
                                      new SqlParameter("@PtChartNo",SqlDbType.VarChar),
                                      new SqlParameter("@DeptCode",SqlDbType.VarChar),
                                      new SqlParameter("@CheckedStatus",SqlDbType.Int)
                                      };
          // 给存储过程参数数组赋值
          paraValues[0].Value = "2017-06-01";
          paraValues[1].Value = "2017-07-01";
          paraValues[2].Value = 1;
          paraValues[3].Value = "";
          paraValues[4].Value = "";
          paraValues[5].Value = "";
          paraValues[6].Value = 1;

          this.dgv_Demo.DataSource = LoadData(strProcName, paraValues);

      }

      /// <summary>
      /// 通过存储过程获取数据
      /// </summary>
      /// <param name="strProcName">存储过程名称</param>
      /// <param name="paraValues">可变的参数数组 数组的个数可以为0,也可以为多个</param>
      /// <returns></returns>
      private DataTable LoadData(string strProcName, params object[] paraValues)
      {
          DataTable dt = new DataTable();
          string strConn = ConfigurationManager.ConnectionStrings["HealthHospInfection"].ConnectionString;
          using (SqlConnection conn = new SqlConnection(strConn))
          {
              try
              {
                  SqlCommand cmd = new SqlCommand();
                  cmd.CommandText = strProcName;
                  // 设置CommandType的类型
                  cmd.CommandType = CommandType.StoredProcedure;
                  cmd.Connection = conn;
                  conn.Open();

                  if (paraValues != null)
                  {
                      //添加参数
                      cmd.Parameters.AddRange(paraValues);
                  }

                  // 取数据
                  using (SqlDataAdapter adapter = new SqlDataAdapter(cmd))
                  {
                      adapter.Fill(dt);
                  }
              }
              catch (Exception ex)
              {
                  MessageBox.Show("错误:" + ex.Message + "/r/n跟踪:" + ex.StackTrace);
              }
              finally
              {
                  conn.Close();
              }
          }
          return dt;
      }
  }
}

 

二、使用SqlCommandBuilder

在上面的例子中,得到一个SqlCommand之后要一个一个地去设置参数,这样很麻烦,幸好SqlCommandBuilder有一个静态的方法:

public static void DeriveParameters(SqlCommand command);

使用这个方法有两个局限性:

  • 1、参数必须是SqlCommand。
  • 2、该方法只能在调用存储过程的时候使用。

同时还要注意到:在使用的时候,数据库连接必须是打开的。
下面的例子演示如何使用这个方法设置存储过程的参数:

using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.Configuration;
using System.Data;
using System.Data.SqlClient;
using System.Drawing;
using System.Linq;
using System.Reflection;
using System.Text;
using System.Windows.Forms;

namespace ExecuteProcBySQLServer
{
  public partial class Form2 : Form
  {
      public Form2()
      {
          InitializeComponent();
      }

      private void btn_LoadData_Click(object sender, EventArgs e)
      {
          // 存储过程名称
          string strProcName = "usp_yngr_getInfectionCard_test";
          // 定义参数类
          object objParams = new
          {
              BeginTime = "2017-06-01",
              EndTime = "2017-07-01",
              DateType = 1,
              PtName = "",
              PtChartNo = "",
              DeptCode = "",
              CheckedStatus = 1
          };

          this.dgv_Demo.DataSource = LoadData(strProcName,objParams);
      }

      private DataTable LoadData(string strProcName,object objParams)
      {
          DataTable dtInit = new DataTable();
          string strConn = ConfigurationManager.ConnectionStrings["HealthHospInfection"].ConnectionString;
          using (SqlConnection conn = new SqlConnection(strConn))
          {
              try
              {
                  SqlCommand cmd = new SqlCommand();
                  cmd.CommandText = strProcName;
                  // 设置CommandType的类型
                  cmd.CommandType = CommandType.StoredProcedure;
                  cmd.Connection = conn;
                  conn.Open();

                  // 添加参数
                  foreach (var item in GetParameters(cmd, objParams))
                  {
                      cmd.Parameters.Add(item);
                  }

                  // 取数据
                  using (SqlDataAdapter adapter = new SqlDataAdapter(cmd))
                  {
                      adapter.Fill(dtInit);
                  }
              }
              catch (Exception ex)
              {
                  MessageBox.Show("错误:" + ex.Message + "/r/n跟踪:" + ex.StackTrace);
              }
              finally
              {
                  conn.Close();
              }
          }
          return dtInit;
      }

      private Collection<SqlParameter> GetParameters(SqlCommand command, object objParam)
      {
          Collection<SqlParameter> collection = new Collection<SqlParameter>();
          if (objParam != null)
          {
              // 使用反射获取属性
              PropertyInfo[] properties = objParam.GetType().GetProperties();
              SqlCommandBuilder.DeriveParameters(command);
              //int index = 0;
              foreach (SqlParameter parameter in command.Parameters)
              {
                  foreach (PropertyInfo property in properties)
                  {
                      if (("@" + property.Name.ToLower()).Equals(parameter.ParameterName.ToLower()))
                      {
                          parameter.Value = property.GetValue(objParam, null);
                          collection.Add(parameter);
                      }
                  }
              }

              // 清空所有参数对象
              command.Parameters.Clear();
          }

          return collection;
      }
  }
}

示例代码下载地址:点此下载

关于C#调用SQL Server中有参数存储过程的文章就介绍到这了。希望对大家的学习有所帮助,也希望大家多多支持编程教程

  上一篇末尾提到了Awaiter这个类型,上一篇说了,能await的对象,必须包含GetAwaiter()方法,不清楚的朋友可以看上篇文章。那么,Awaiter到底有什么特别之处呢?&# ...