DataTable数据集转换为List非泛型以及泛型方式
前言
DataTable是断开式的数据集合,所以一旦从数据库获取,就会在内存中创建一个数据的副本,以便使用。由于在实际项目中,经常会将DataTable中的每行数据转换为Model,然后放到List集合中,所以,下面提供了转换的两种思路:非泛型转换思路和泛型转换思路。
非泛型方式
首先来说下非泛型转换,这种转换方式就是通过遍历DataTable,然后向Model中的相同字段中赋值即可。
//使用Linq的ToList方法,非泛型
public static List<Entity> ConvertTo(DataTable dt)
{
if (dt == null) return null;
if (dt.Rows.Count <= 0) return null;
List<Entity> list = new List<Entity>();
list = (from DataRow dr in dt.Rows
select new Entity
{
PID = Int32.Parse(dr["PID"].ToString()),
PName = dr["PName"].ToString(),
PPass = dr["PPass"].ToString(),
PAddr = dr["PAddr"].ToString()
}).ToList();
return list;
}
代码很简单,就是通过循环赋值而已。这里我用的Model测试类如下:
namespace DataSetToEntity.Code
{
public class Entity
{
public int PID { get; set; }
public string PName { get; set; }
public string PPass { get; set; }
public string PAddr { get; set; }
}
}
泛型方式
然后,由于非泛型的版本不具有通用性,所以这里我们准备用泛型版本来实现一下,由于泛型版本是不可预知Model中的属性结构的,所以这里我们需要引入反射来进行操作。
//使用反射的泛型方法一
public static List<T> ConvertTo<T>(DataTable dt) where T : new()
{
if (dt == null) return null;
if (dt.Rows.Count <= 0) return null;
List<T> list = new List<T>();
try
{
List<string> columnsName = new List<string>();
foreach (DataColumn dataColumn in dt.Columns)
{
columnsName.Add(dataColumn.ColumnName);//得到所有的表头
}
list = dt.AsEnumerable().ToList().ConvertAll<T>(row => getObject<T>(row, columnsName)); //转换
return list;
}
catch (Exception ex)
{
return null;
}
}
public static T getObject<T>(DataRow row, List<string> columnsName) where T : new()
{
T obj = new T();
try
{
string columnname = "";
string value = "";
PropertyInfo[] Properties = typeof(T).GetProperties();
foreach (PropertyInfo objProperty in Properties) //遍历T的属性
{
columnname = columnsName.Find(name => name.ToLower() == objProperty.Name.ToLower()); //寻找可以匹配的表头名称
if (!string.IsNullOrEmpty(columnname))
{
value = row[columnname].ToString();
if (!string.IsNullOrEmpty(value))
{
if (Nullable.GetUnderlyingType(objProperty.PropertyType) != null) //存在匹配的表头
{
value = row[columnname].ToString().Replace("$", "").Replace(",", ""); //从dataRow中提取数据
objProperty.SetValue(obj, Convert.ChangeType(value, Type.GetType(Nullable.GetUnderlyingType(objProperty.PropertyType).ToString())), null); //赋值操作
}
else
{
value = row[columnname].ToString().Replace("%", ""); //存在匹配的表头
objProperty.SetValue(obj, Convert.ChangeType(value, Type.GetType(objProperty.PropertyType.ToString())), null);//赋值操作
}
}
}
}
return obj;
}
catch
{
return obj;
}
}
上面主要是通过反射获取T的属性名称,然后和DataRow中的表头相匹配,如果匹配的上,就赋值。下面是其简化版本:
//使用反射的泛型方法二
public static List<T> ConvertToEx<T>(DataTable dt) where T : new()
{
if (dt == null) return null;
if (dt.Rows.Count <= 0) return null;
List<T> list = new List<T>();
Type type = typeof(T);
PropertyInfo[] propertyInfos = type.GetProperties(); //获取泛型的属性
List<DataColumn> listColumns = dt.Columns.Cast<DataColumn>().ToList(); //获取数据集的表头,以便于匹配
T t;
foreach (DataRow dr in dt.Rows)
{
t = new T();
foreach (PropertyInfo propertyInfo in propertyInfos)
{
try
{
DataColumn dColumn = listColumns.Find(name => name.ToString().ToUpper() == propertyInfo.Name.ToUpper()); //查看是否存在对应的列名
if (dColumn != null)
propertyInfo.SetValue(t, dr[propertyInfo.Name], null); //赋值
}
catch (Exception ex)
{
throw new Exception(ex.Message);
}
}
list.Add(t);
}
return list;
}
List<Entity> list = CommonUtils.ConvertToEx<Entity>(dt);
DataTable数据集转换为List非泛型以及泛型方式的更多相关文章
- C#高级语法之泛型、泛型约束,类型安全、逆变和协变(思想原理)
一.为什么使用泛型? 泛型其实就是一个不确定的类型,可以用在类和方法上,泛型在声明期间没有明确的定义类型,编译完成之后会生成一个占位符,只有在调用者调用时,传入指定的类型,才会用确切的类型将占位符替换 ...
- 数据集转换为Json
数据集转换为Json 第一步:新建一个类对象 通常我会写三个属性:状态.返回信息.数据集 第二步:新建一个JSON转换类 第三步:把类对象当做参数传入JSON转换类 ———————————————— ...
- 【学习笔记】C#中的泛型和泛型集合
一.什么是泛型? 泛型是C#语言和公共语言运行库(CLR)中的一个新功能,它将类型参数的概念引入.NET Framework.类型参数使得设计某些类和方法成为可能,例如,通过使用泛型类型参数T,可以大 ...
- mormot 数据集转换为JSON字串
mormot 数据集转换为JSON字串 unit Unit1; interface uses Windows, Messages, SysUtils, Variants, Classes, Graph ...
- Scala 深入浅出实战经典 第42讲:scala 泛型类,泛型函数,泛型在spark中的广泛应用
王家林亲授<DT大数据梦工厂>大数据实战视频 Scala 深入浅出实战经典(1-64讲)完整视频.PPT.代码下载:百度云盘:http://pan.baidu.com/s/1c0noOt6 ...
- DataTable 对象 转换为Json 字符串
/// <summary> /// DataTable 对象 转换为Json 字符串 /// </summary> /// <param name="dt&qu ...
- Java基础---Java---基础加强---内省的简单运用、注解的定义与反射调用、 自定义注解及其应用、泛型及泛型的高级应用、泛型集合的综合
内省的简单运用: JavaBean是一种特殊的Java类,主要用于传递数据信息,这种java类中的方法主要用于访问私有的字段,且方法名符合某种命名规则. 采用遍历BeanInfo的所有属性方式来查找和 ...
- JavaSE学习总结(十六)—— 泛型与泛型应用
一.泛型概要 泛型(Generic)的本质是类型参数化,通俗的说就是用一个占位符来表示类型,这个类型可以是String,Integer等不确定的类型,表明可接受的类型. 泛型是Java中一个非常重要的 ...
- .NET泛型02,泛型的使用
在" .NET泛型01,为什么需要泛型,泛型基本语法"中,了解了泛型的基本概念,本篇偏重于泛型的使用.主要包括: ■ 泛型方法重载需要注意的问题■ 泛型的类型推断■ 泛型方法也可以 ...
随机推荐
- Swift开发第六篇——操作运算符也可以重载& func 的参数修饰
本篇分为两部分: 1.Swift 中重载操作运算符的使用 2.Swfit 中 func 的参数修饰 1.Swift 中重载操作运算符的使用 与别的语言不同,Swift 支持运算符的重载,运算符指的是“ ...
- VIP - virtual IP address
virtual IP address (虚拟 IP 地址)1.是集群的ip地址,一个vip对应多个机器2.与群集关联的唯一 IP 地址 see wiki: A virtual IP address ( ...
- Effective Java 58 Use checked exceptions for recoverable conditions and runtime exceptions for programming errors
Three kinds of throwables Throwables Checked Recoverable checked exceptions Y Y runtime exceptions N ...
- 用mciSendString做音乐播放器
音乐操作类 public class clsMCI { public clsMCI() { // // TODO: 在此处添加构造函数逻辑 // } //定义API函数使用的字符串变量 [Marsha ...
- Centos Ping不通外网
安装完成Vm,Centos6.5,设置了网络: 1.VM虚拟网络,采用桥接模式. 2.Centos里各种 设置ifcfg-eth0中的GETWAY,ADDIP等等 vim /etc/sysconfig ...
- Linux运维工程师入门须掌握的10个技术点
本人是linux运维工程师,对这方面有点心得,现在我说说要掌握哪方面的工具吧 说到工具,在行外可以说是技能,在行内我们一般称为工具,就是运维必须要掌握的工具. 我就大概列出这几方面,这样入门就基本没问 ...
- 使用Azure Automation(自动化)定时关闭和启动虚拟机
1. 概述 作为Windows Azure的用户,使用Azure的过程中,最担心的事情就是还没到月底,预设的费用就快消耗完了(下面两张账单图是我最讨厌看到的).但是仔细分析自己的费用列表,发现绝大部分 ...
- listview中OnItemClick方法各个参数的作用
OnItemClick(AdapterView<?> arg0, View arg1, int arg2, long arg3) 1.arg0,arg2 m_listview.setOnI ...
- 广度优先搜索 codevs 2806 红与黑
codevs 2806 红与黑 时间限制: 1 s 空间限制: 64000 KB 题目等级 : 白银 Silver 题目描述 Description 有一个矩形房间,覆盖正方形瓷砖.每块瓷砖 ...
- win8程序开机自启动管理
主要介绍利用系统自身的工具来管理开机自启动,而非第三方的工具,自己了解了,也写出来分享给大家@.·.@ 1.程序设置开机自启动 a. 打开计算机资源管理器-->进入"C:\Progra ...