转:SQLHelper类,泛型+反射

        自己一直都是学习使用asp.net mvc框架+linQ的,所以对于ado.net基本上一无所知,最近接了个小项目,所以打算学习+用ado.net来完成。
        首先就想到了,写一个通用点SQLHelper类来辅助完成数据库的操作。

1.定义一个类:public class SQLHelper<T> where T : class, new()
        说明:SQLHelper有一个T的泛型类型,T属于class,new(),否则T就不能T t =new T()这样使用new关键字了!

2.之后就是数据库的链接和关闭等操作:


 1         /// <summary>
 2         /// 链接数据库字符串
 3         /// </summary>
 4         public static string strConnectionString = ConfigurationManager.ConnectionStrings["DataConnectionString"].ToString();
 5 
 6         /// <summary>
 7         /// 数据库连接
 8         /// </summary>
 9         public SqlConnection Connection = null;
10 
11         public SQLHelper()
12         {
13             OpenConnect();
14         }
15 
16         /// <summary>
17         /// 打开数据库连接
18         /// </summary>
19         public void OpenConnect()
20         {
21             if (Connection == null || Connection.State != System.Data.ConnectionState.Open)
22             {
23                 Connection = new SqlConnection(strConnectionString);
24 
25                 Connection.Open();
26             }
27         }
28 
29         /// <summary>
30         /// 关闭数据库连接
31         /// </summary>
32         public void CloseConnect()
33         {
34             if (Connection != null && Connection.State != System.Data.ConnectionState.Closed)
35             {
36                 Connection.Close();
37             }
38         }


3.对数据库进行读写操作。


 1 
 2         /// <summary>
 3         /// 执行查询语句
 4         /// </summary>
 5         /// <param name="strSQL">SQL语句</param>
 6         /// <param name="obQuery">SQL参数的值</param>
 7         /// <returns></returns>
 8         public SqlDataReader ExecReader(string strSQL, object obQuery)
 9         {
10             SqlCommand command = new SqlCommand(strSQL, Connection);
11 
12             if (obQuery != null)
13             {
14                 PropertyInfo[] pis = obQuery.GetType().GetProperties();
15 
16                 foreach (var p in pis)
17                 {
18                     command.Parameters.Add(new SqlParameter(p.Name, p.GetValue(obQuery, null)));
19                 }
20             }
21 
22             SqlDataReader reader = command.ExecuteReader();
23 
24             return reader;
25         }
26 
27         /// <summary>
28         /// 执行返回单值的查询语句
29         /// </summary>
30         /// <param name="strSQL">SQL语句</param>
31         /// <param name="obQuery">SQL参数的值</param>
32         /// <returns></returns>
33         public object ExecSingleValue(string strSQL, object obQuery)
34         {
35             SqlCommand command = new SqlCommand(strSQL, Connection);
36 
37 
38             if (obQuery != null)
39             {
40                 PropertyInfo[] pis = obQuery.GetType().GetProperties();
41 
42                 foreach (var p in pis)
43                 {
44                     command.Parameters.Add(new SqlParameter(p.Name, p.GetValue(obQuery, null)));
45                 }
46             }
47 
48             return command.ExecuteScalar();
49         }
50 
51         /// <summary>
52         /// 执行非查询语句
53         /// </summary>
54         /// <param name="strSQL">SQL语句</param>
55         /// <param name="obQuery">SQL参数的值</param>
56         /// <returns></returns>
57         public int ExecNoQuery(string strSQL, object obQuery)
58         {
59             SqlCommand command = new SqlCommand(strSQL, Connection);
60 
61             if (obQuery != null)
62             {
63                 PropertyInfo[] pis = obQuery.GetType().GetProperties();
64 
65                 foreach (var p in pis)
66                 {
67                     command.Parameters.Add(new SqlParameter(p.Name, p.GetValue(obQuery, null)));
68                 }
69             }
70 
71             return command.ExecuteNonQuery();
72         }

解释:
        //判断是SQL语句中参数的值对象是否为空
        //例如:new{Id=1,Name="Test"}
            if (obQuery != null)
            {
            //获取SQL语句中参数的值对象中的属性类型和值
                PropertyInfo[] pis = obQuery.GetType().GetProperties();
            //循环遍历对象中的属性
                foreach (var p in pis)
                {
              //利用反射将Id,Name等值填充到SQL语句中的参数中
                    command.Parameters.Add(new SqlParameter(p.Name, p.GetValue(obQuery, null)));
                }
            }

查询操作中,返回的是SQLDataReader对象,如何获取我们所需要的列表,分页,单个实体呢?
4.返回列表List<T>,还是利用泛型+反射


 1         /// <summary>
 2         /// 获取列表
 3         /// </summary>
 4         /// <param name="strSQL">SQL语句</param>
 5         /// <param name="obQuery">SQL参数的值</param>
 6         /// <returns></returns>
 7         public List<T> GetList(string strSQL, object obQuery)
 8         {
 9             //调用执行查询语句函数,返回SqlDataReader
10             SqlDataReader reader = ExecReader(strSQL, obQuery);
11             //定义返回的列表
12             List<T> list = new List<T>();
13             //定义T类型的实体
14             T model = new T();
15             //获取T类型实体的属性类型和值
16             PropertyInfo[] pis = model.GetType().GetProperties();
17             //获取数据库返回的列数
18             int intColCount = reader.FieldCount;
19             //遍历SqlDataReader
20             while (reader.Read())
21             {
22                 //定义
23                 int value_number = 0;
24                 //重新实例化T
25                 model = new T();
26                 //从数据库拿出一条数据后,循环遍历T类型的属性类型和值
27                 for (int i = 0; i < intColCount; i++)
28                 {
29                     //判断第一列是否为row_number,此为分页使用
30                     if (reader.GetName(i) == "row_number") value_number++;
31                     //设置T对应属性的值
32                     pis[i].SetValue(model, reader.GetValue(value_number), null);
33                     value_number++;
34                 }
35                 //将T添加到列表中
36                 list.Add(model);
37             }
38 
39             return list;
40         }


5.返回分页,获取PagesList<T>
5.1。分页实体类:


 1 public class PagedList<T> : List<T>
 2     {
 3         /// <summary>
 4         /// 分页编号
 5         /// </summary>
 6         public int intPageIndex { getset; }
 7 
 8         /// <summary>
 9         /// 分页大小
10         /// </summary>
11         public int intPageSize { getset; }
12 
13         /// <summary>
14         /// 分页数
15         /// </summary>
16         public int intPages { getset; }
17 
18         /// <summary>
19         /// 总元素的个数
20         /// </summary>
21         public int intTotalCount { getset; }
22 
23         /// <summary>
24         /// 此分页元素的个数
25         /// </summary>
26         public int intCount { getset; }
27 
28         /// <summary>
29         /// 是否有下一页
30         /// </summary>
31         public bool HasNextPage { getset; }
32 
33         /// <summary>
34         /// 是否有上一页
35         /// </summary>
36         public bool HasPrPage { getset; }
37 
38         public PagedList(int intPageIndex, int intPageSize)
39         {
40             this.intPageIndex = intPageIndex;
41             this.intPageSize = intPageSize;
42         }
43     }


5.2。实现分页,返回PagesList<T>


 1         /// <summary>
 2         /// 获取分页
 3         /// </summary>
 4         /// <param name="strTotalSQL">总共个数的SQL</param>
 5         /// <param name="obTotalQuery">总共个数的SQL参数的值</param>
 6         /// <param name="strSQL">分页的SQL</param>
 7         /// <param name="obQuery">分页SQL参数的值</param>
 8         /// <param name="intPageIndex">分页编号</param>
 9         /// <param name="intPageSize">分页大小</param>
10         /// <returns></returns>
11         public PagedList<T> GetPageList(string strTotalSQL, object obTotalQuery, string strSQL, object obQuery, int intPageIndex, int intPageSize)
12         {
13             //定义分页对象的编号和大小
14             PagedList<T> pageList = new PagedList<T>(intPageIndex, intPageSize);
15             //执行获取单个值的函数,设置分页对象的总元素
16             pageList.intTotalCount = (int)ExecSingleValue(strTotalSQL, obTotalQuery);
17             //设置分页对象的分页数
18             if (pageList.intTotalCount % intPageSize == 0) pageList.intPages = pageList.intTotalCount / intPageSize;
19             else pageList.intPages = pageList.intTotalCount / intPageSize + 1;
20             //定义列表,调用获取列表的函数获取此分页的元素
21             List<T> list = GetList(strSQL, obQuery);
22             //将列表元素添加到分页对象当中
23             pageList.AddRange(list);
24             //设置分页对象是否有上一页和下一页
25             pageList.HasNextPage = pageList.intPageIndex < pageList.intPages ? true : false;
26             pageList.HasPrPage = pageList.intPageIndex > 1 ? true : false;
27 
28             return pageList;
29         }


6.获取单个实体类:T


 1         /// <summary>
 2         /// 获取单个实体
 3         /// </summary>
 4         /// <param name="strSQL">SQL语句</param>
 5         /// <param name="obQuery">SQL参数的值</param>
 6         /// <returns></returns>
 7         public T GetTM(string strSQL, object obQuery)
 8         {
 9             //调用执行查询语句,返回SqlDataReader
10             SqlDataReader reader = ExecReader(strSQL, obQuery);
11             //新建一个T类型
12             T model = new T();
13             //获取T类型的属性类型和值
14             PropertyInfo[] pis = model.GetType().GetProperties();
15             //获取数据库返回数据的列数
16             int intColCount = reader.FieldCount;
17             //读取数据,填充T
18             if (reader.Read())
19             {
20                 int value_number = 0;
21                 for (int i = 0; i < intColCount; i++)
22                 {
23                     pis[i].SetValue(model, reader.GetValue(value_number), null);
24                     value_number++;
25                 }
26             }
27 
28             return model;
29         }


7.调用方法:ResumeTM为数据库表的实体类


 1 public List<ResumeTM> GetResumeByJobInfoId(int intJobInfoId)
 2         {
 3             SQLHelper<ResumeTM> helper = new SQLHelper<ResumeTM>();
 4 
 5             string strSQL = @"select * from Resume where FirstJobId=@JobInfoId or SecondJobId=@JobInfoId order by CreateTime desc";
 6 
 7             object obQuery = new { JobInfoId=intJobInfoId};
 8 
 9             List<ResumeTM> list = helper.GetList(strSQL, obQuery);
10 
11             helper.CloseConnect();
12 
13             return list;
14         }
15 
16         public ResumeTM GetResumeById(int intId)
17         {
18             SQLHelper<ResumeTM> helper = new SQLHelper<ResumeTM>();
19 
20             string strSQL = @"select * from Resume where Id=@Id";
21 
22             object obQuery = new { Id=intId};
23 
24             ResumeTM tm = helper.GetTM(strSQL, obQuery);
25 
26             helper.CloseConnect();
27 
28             return tm;
29         }
30 
31         public PagedList<ResumeTM> GetResume(int intPageIndex, int intPaegSize)
32         {
33             SQLHelper<ResumeTM> helper = new SQLHelper<ResumeTM>();
34 
35             string strTotalCount = @"select count(*) from Resume";
36 
37             string strSQL = @"select * from
38                              (
39                                 select row_number() over(order by CreateTime desc) as row_number,* from Resume
40                              ) as t0
41                             where t0.row_number between @intPageSize*(@intPageIndex-1)+1 and @ingPageSize*@intPageIndex";
42             object obQuery = new { intPageSize=intPaegSize,intPageIndex=intPageIndex};
43 
44             PagedList<ResumeTM> list = helper.GetPageList(strTotalCount, null, strSQL, obQuery, intPageIndex, intPaegSize);
45 
46             helper.CloseConnect();
47 
48             return list;
49         }
50 
51         public void Delete(int intId)
52         {
53             SQLHelper<ResumeTM> helper = new SQLHelper<ResumeTM>();
54 
55             string strSQL = @"delete from Resume where Id=@Id";
56 
57             object obQuery = new { Id=intId};
58 
59             helper.ExecNoQuery(strSQL, obQuery);
60 
61             helper.CloseConnect();
62         }


哈哈。。写好了。。。有什么写得不好的,希望大家多多指教。拍拍砖。。。

原文地址:https://www.cnblogs.com/dudu837/p/1561240.html