c#利用反射+特性实现简单的实体映射数据库操作类实现自动增删改查(一)
///對字段特性的映射類
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Data;
namespace Attributes
{
??? [AttributeUsage(AttributeTargets.Property, AllowMultiple = false, Inherited = false)]
??? public class FieldAttribute : Attribute
??? {
??????? private string _Fields;
??????? /// <summary>
??????? /// 字段名稱
??????? /// </summary>
??????? public string Fields
??????? {
??????????? get { return _Fields; }
??????? }
??????? private DbType _Dbtype;
??????? /// <summary>
??????? /// 字段類型
??????? /// </summary>
??????? public DbType Dbtype
??????? {
??????????? get { return _Dbtype; }
??????? }
??????? private int _ValueLength;
??????? /// <summary>
??????? /// 字段值長度
??????? /// </summary>
??????? public int ValueLength
??????? {
??????????? get { return _ValueLength; }
??????? }
??????? private bool _PK_Primary;
??????? /// <summary>
??????? /// 是否是主鍵
??????? /// </summary>
??????? public bool PK_Primary
??????? {
??????????? get { return _PK_Primary; }
??????? }
??????? /// <summary>
??????? /// 構造函數
??????? /// </summary>
??????? /// <param name="fields"> 字段名</param>
??????? /// <param name="types"> 字段類型</param>
??????? /// <param name="i"> 字段值長度</param>
??????? public FieldAttribute(string fields, DbType types, int i,bool PK=false)
??????? {
??????????? _Fields = fields;
??????????? _Dbtype = types;
??????????? _PK_Primary = PK;
??????????? _ValueLength = i;
??????? }
??? }
}
///對表特性的映射類
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
namespace Attributes
{
??? [AttributeUsage(AttributeTargets.Class, AllowMultiple = false, Inherited = false)]
??? public class TableAttribute : Attribute
??? {
??????? private string _TableName;
??????? /// <summary>
??????? /// 映射的表名
??????? /// </summary>
??????? public string TableName
??????? {
??????????? get { return _TableName; }
??????? }
??????? /// <summary>
??????? /// 定位函數映射表名;
??????? /// </summary>
??????? /// <param name="table"></param>
??????? public TableAttribute(string table)
??????? {
??????????? _TableName = table;
??????? }
??? }
}
公共方法?
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Data;
using System.Reflection;
namespace Attributes
{
??? /// <summary>
??? /// 處理反射的類
??? /// </summary>
??? /// <typeparam name="T"> 與數據庫表建立聯系的類</typeparam>
??? public class AttributesContext<T>
??? {
??????? /// <summary>
??????? ///存放AttributesContext 類中所有的當前錯誤信息
??????? /// </summary>
??????? private string ExceptionBug;
??????? /// <summary>
??????? /// 讀取映射的表名
??????? /// </summary>
??????? /// <param name="Info">自定義類型</param>
??????? /// <returns>放回建立映射表名 沒簡歷表面返回空</returns>
??????? public string xTable(T Info)
??????? {
??????????? Type userAttu = Info.GetType();
??????????? try
??????????? {
??????????????? TableAttribute tables = (TableAttribute)userAttu.GetCustomAttributes(false)[0];
??????????????? //在TableAttribute中我設置的是不容許多個特性所取 【0】
??????????????? return tables.TableName;
??????????? }
??????????? catch (ArgumentNullException e)
??????????? {
??????????????? ExceptionBug = e.Message;
??????????????? return null;
??????????? }
??????????? catch (NotSupportedException e1)
??????????? {
??????????????? ExceptionBug = e1.Message;
??????????????? return null;
??????????? }
??????????
??????? }
??????? /// <summary>
??????? /// 放回自定義類與表建立的映射的字段名
??????? /// </summary>
??????? /// <param name="Info">與表建立映射聯系的類</param>
??????? /// <returns>表字段的數組Dictionary?? FieldAttribute ,Object[]| key 字段名 FieldAttribute ,value需要自己轉換;object [2]? 其中第一個是字段名稱? 第2個是字段值 </returns>
??????? public Dictionary<FieldAttribute, Object[]> xField(T Info)
??????? {
??????????? Dictionary<FieldAttribute, Object[]> xFields = new Dictionary<FieldAttribute, Object[]>();
??????????
??????????? Type types = Info.GetType();
??????????? PropertyInfo[] typesPro = types.GetProperties();
??????????? foreach (PropertyInfo pro in typesPro)
??????????? {
??????????????? object[] attu = pro.GetCustomAttributes(false);
??????????????? object objValue = pro.GetGetMethod().Invoke(Info, null);//取特性描述相應字段的值
??????????????? object objFieldName = (Object)pro.Name;//取特性對應類的字段名稱
??????????????? object[] classInfo = new object[2];//把類中的字段名稱與值存放;
???????????????
??????????????? classInfo[0] = objFieldName;
??????????????? classInfo[1] = objValue;
??????????????? foreach (Attribute afield in attu)
?????????????? {
?????????????????? if (afield is FieldAttribute)
?????????????????? {
?????????????????????? FieldAttribute column = afield as FieldAttribute;//把afield轉換成FieldAttribute類型
?????????????????????? xFields.Add(column, classInfo);//把字段存放到key 把特性描述的字段字存放到value
???????????????????
?????????????????? }
???????????????????
?????????????? }
??????????? }
??????????? return xFields;
??????? }
??? }
}
用AttributesContext中的? public Dictionary<FieldAttribute, Object[]> xField(T Info)
我們可以獲得字段與特性以及值的Dictionary?? 當我們知道 Dictionary就可以取出相應的信息讓后我們在拼接一下 就可以獲得命令語句;
我寫得是拼接的字符串下面是列子;
??? /// <summary>
??? /// 用來拼接操作數據庫的字符串
??? /// </summary>
??? /// <typeparam name="T"></typeparam>
??? public class Install<T>
??? {
??????? /// <summary>
??????? /// 拼接查詢字符串(只能用在與表建立聯系的實體類)
??????? /// </summary>
??????? /// <param name="types"> 與表建立映射的自定義類</param>
??????? /// <returns>查詢字符串</returns>
??????? public string insertDate(T types)
??????? {
??????????? string cmdtxt = "insert into ";
??????????? string cmdparVar = null;
??????????? Type userAttu = types.GetType();
??????????? TableAttribute? tables = (TableAttribute )userAttu.GetCustomAttributes(false)[0];
??????????? cmdtxt += tables.TableName + "(";
??????????? PropertyInfo[] info = userAttu.GetProperties();
??????????? foreach (PropertyInfo prs in info)
??????????? {
??????????????? object[] attu = prs.GetCustomAttributes(false);
??????????????? foreach (Attribute abute in attu)
??????????????? {
??????????????????? if (abute is FieldAttribute)
??????????????????? {
??????????????????????? FieldAttribute midle = abute as FieldAttribute;
???????????????????????? cmdtxt +=? midle.Fields + ",";
???????????????????????? object obj = prs.GetGetMethod().Invoke(types,null);
??????????????????????? if (midle.Dbtype == DbType.Int32)
??????????????????????????? cmdparVar +=? obj + ",";
??????????????????????? else
??????????????????????????? cmdparVar+="'"+obj +"',";
??????????????????????
??????????????????? }
??????????????? }
???????????????
??????????? }
??????????? cmdparVar = cmdparVar.Substring(0, cmdparVar.Length - 1);
??????????? cmdtxt = cmdtxt.Substring(0, cmdtxt.Length - 1) + ")";
??????????? cmdtxt += "values(" + cmdparVar + ")";
??????????? return cmdtxt;
??????? }
同理我們可以拼接出其他語句; 這只是思路 我還沒優化以及錯誤處理; 還可以改進 改為參數化查詢 在特性中不是有類型 字段長度的嘛!那我們就可以利用參數化列;
下面是我寫的自動創建參數化對象
?? /// <summary>
??????? /// 創建存儲過程的參數? 只用于 (SQL語法)
??????? /// </summary>
??????? /// <param name="parName">參數名(與存儲過程參數名一樣)</param>
??????? /// <param name="parType">參數的數據類型</param>
??????? /// <param name="parSize">參數字段長度 int 用0表示長度</param>
??????? /// <param name="parVal">輸入參數的值</param>
??????? /// <param name="aspect">傳入方式</param>
??????? /// <returns></returns>
??????? public static SqlParameter CreateProcParameters(string parName, SqlDbType parType, int parSize, object parVal, ParameterDirection aspect = ParameterDirection.Input)
??????? {
??????????? SqlParameter p = new SqlParameter();
??????????? p.ParameterName = parName;
??????????? p.SqlDbType = parType;
??????????? p.Direction = aspect;
??????????? if (parSize != 0)
??????????????? p.Size = parSize;
??????????? p.SqlValue = parVal;
??????????? return p;
??????? }
循環添加參數到命令中
?public static void AddParametersTocmd(SqlCommand cmd,params SqlParameter[] pList)
??????? {
??????????? foreach (SqlParameter s in pList)
??????????? {
??????????????? cmd.Parameters.Add(s);//添加參數
??????????? }
??????? }
| 下次有時候在把完整的實現表與類的映射實現自動化增刪改查些出來; 我也才開始學習哪些對象我也只是猜實現 還沒進行優化所以等下次我 我在發表; |
轉載于:https://www.cnblogs.com/aw25220/archive/2011/04/24/2026561.html
創作挑戰賽新人創作獎勵來咯,堅持創作打卡瓜分現金大獎總結
以上是生活随笔為你收集整理的c#利用反射+特性实现简单的实体映射数据库操作类实现自动增删改查(一)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 事件概念和事件监听
- 下一篇: [C# 基础知识系列]专题六:泛型基础篇