C# 如何将数据表转换为动态对象?

C# 如何将数据表转换为动态对象?,c#,dynamic,datatable,ienumerable,C#,Dynamic,Datatable,Ienumerable,如何在IEnumerable中转换DataTable 例如,我想转换任何DataTable ID | Name DI | emaN --------- or --------- 1 | x 2 | x 2 | y 1 | y 在对象列表中 // list 1 (ex 1) // list 2 (ex 2) {

如何在
IEnumerable
中转换
DataTable

例如,我想转换任何
DataTable

ID | Name          DI | emaN
---------    or    ---------
 1 | x              2 | x
 2 | y              1 | y
在对象列表中

// list 1      (ex 1)             // list 2    (ex 2)
{                                 {
  { ID = 1, Name = "x" }            { DI = 2, emaN = "x" }
  { ID = 2, Name = "y" }            { DI = 1, emaN = "y" }
}                                 }
所以

我怎么做呢?

试试看

var MyResult = from x in MyDataTable select new { ID = x["ID"], Name = x["Name"] }.ToList ();

有些ORM可以直接从DB读取到
动态ExpandooObject
。例如(在这里阅读)

或者你也可以尝试类似的方法:

var dt = new DataTable();

var dns = new List<dynamic>();

foreach (var item in dt.AsEnumerable())
{
    // Expando objects are IDictionary<string, object>
    IDictionary<string, object> dn = new ExpandoObject();

    foreach (var column in dt.Columns.Cast<DataColumn>())
    {
        dn[column.ColumnName] = item[column];
    }

    dns.Add(dn);
}

// Now you can do something like dns[0].MyColumnName 
// or recast to IDictionary<string, object> and do 
// something like casted["MyColumnName"]
var dt=new DataTable();
var dns=新列表();
foreach(dt.AsEnumerable()中的变量项)
{
//Expando对象是IDictionary对象
IDictionary dn=新的ExpandooObject();
foreach(dt.Columns.Cast()中的var列)
{
dn[column.ColumnName]=项[column];
}
dns.Add(dn);
}
//现在您可以执行类似dns[0]的操作
//或重铸到IDictionary并执行
//类似于casted[“MyColumnName”]
课程计划
{
静态void Main()
{
var dt=新数据表();
添加(“ID”,typeof(int));
添加(“名称”,类型(字符串));
增加(1,“x”);
增加(2,“y”);
List dynamicDt=dt.ToDynamic();
Console.WriteLine(dynamicDt.First().ID);
Console.WriteLine(dynamicDt.First().Name);
}
}
公共静态类DataTableExtensions
{
公共静态列表到动态(此数据表dt)
{
var dynamicDt=新列表();
foreach(数据行中的数据行)
{
dynamic dyn=新的ExpandoObject();
动态添加(dyn);
foreach(dt.Columns中的DataColumn列)
{
变量dic=(i词典)dyn;
dic[column.ColumnName]=行[column];
}
}
返回动态CDT;
}
}
如何使用:


将数据表转换为列表

    #region "Convert DataTable to List<dynamic>"

    public List<dynamic> ToDynamicList(DataTable dt)
    {
        List<string> cols = (dt.Columns.Cast<DataColumn>()).Select(column => column.ColumnName).ToList();
        return ToDynamicList(ToDictionary(dt), getNewObject(cols));
    }
    public List<Dictionary<string, object>> ToDictionary(DataTable dt)
    {
        var columns = dt.Columns.Cast<DataColumn>();
        var Temp = dt.AsEnumerable().Select(dataRow => columns.Select(column =>
                             new { Column = column.ColumnName, Value = dataRow[column] })
                         .ToDictionary(data => data.Column, data => data.Value)).ToList();
        return Temp.ToList();
    }
    public List<dynamic> ToDynamicList(List<Dictionary<string, object>> list, Type TypeObj)
    {
        dynamic temp = new List<dynamic>();
        foreach (Dictionary<string, object> step in list)
        {
            object Obj = Activator.CreateInstance(TypeObj);
            PropertyInfo[] properties = Obj.GetType().GetProperties();
            Dictionary<string, object> DictList = (Dictionary<string, object>)step;
            foreach (KeyValuePair<string, object> keyValuePair in DictList)
            {
                foreach (PropertyInfo property in properties)
                {
                    if (property.Name == keyValuePair.Key)
                    {
                        property.SetValue(Obj, keyValuePair.Value.ToString(), null);
                        break;
                    }
                }
            }
            temp.Add(Obj);
        }
        return temp;
    }       
    private Type getNewObject(List<string> list)
    {
        AssemblyName assemblyName = new AssemblyName();
        assemblyName.Name = "tmpAssembly";
        AssemblyBuilder assemblyBuilder = Thread.GetDomain().DefineDynamicAssembly(assemblyName, AssemblyBuilderAccess.Run);
        ModuleBuilder module = assemblyBuilder.DefineDynamicModule("tmpModule");
        TypeBuilder typeBuilder = module.DefineType("WebgridRowCellCollection", TypeAttributes.Public);
        foreach (string step in list)
        {
            string propertyName = step;
            FieldBuilder field = typeBuilder.DefineField(propertyName, typeof(string), FieldAttributes.Public);
            PropertyBuilder property = typeBuilder.DefineProperty(propertyName, System.Reflection.PropertyAttributes.None, typeof(string), new Type[] { typeof(string) });
            MethodAttributes GetSetAttr = MethodAttributes.Public | MethodAttributes.HideBySig;
            MethodBuilder currGetPropMthdBldr = typeBuilder.DefineMethod("get_value", GetSetAttr, typeof(string), Type.EmptyTypes);
            ILGenerator currGetIL = currGetPropMthdBldr.GetILGenerator();
            currGetIL.Emit(OpCodes.Ldarg_0);
            currGetIL.Emit(OpCodes.Ldfld, field);
            currGetIL.Emit(OpCodes.Ret);
            MethodBuilder currSetPropMthdBldr = typeBuilder.DefineMethod("set_value", GetSetAttr, null, new Type[] { typeof(string) });
            ILGenerator currSetIL = currSetPropMthdBldr.GetILGenerator();
            currSetIL.Emit(OpCodes.Ldarg_0);
            currSetIL.Emit(OpCodes.Ldarg_1);
            currSetIL.Emit(OpCodes.Stfld, field);
            currSetIL.Emit(OpCodes.Ret);
            property.SetGetMethod(currGetPropMthdBldr);
            property.SetSetMethod(currSetPropMthdBldr);
        }
        Type obj = typeBuilder.CreateType();
        return obj;
    }

    #endregion
#区域“将数据表转换为列表”
公共列表到动态列表(数据表dt)
{
List cols=(dt.Columns.Cast()).Select(column=>column.ColumnName.ToList();
返回到dynamiclist(ToDictionary(dt)、getNewObject(cols));
}
公共列表到字典(数据表dt)
{
var columns=dt.columns.Cast();
var Temp=dt.AsEnumerable().Select(数据行=>columns.Select(列=>
新{Column=Column.ColumnName,Value=dataRow[Column]})
.ToDictionary(data=>data.Column,data=>data.Value)).ToList();
返回温度ToList();
}
公共列表到动态列表(列表列表,键入TypeObj)
{
动态临时=新列表();
foreach(字典步骤列表)
{
object Obj=Activator.CreateInstance(TypeObj);
PropertyInfo[]properties=Obj.GetType().GetProperties();
Dictionary DictList=(Dictionary)步骤;
foreach(DictList中的KeyValuePair KeyValuePair)
{
foreach(属性中的PropertyInfo属性)
{
if(property.Name==keyValuePair.Key)
{
SetValue(Obj,keyValuePair.Value.ToString(),null);
打破
}
}
}
温度添加(Obj);
}
返回温度;
}       
私有类型getNewObject(列表)
{
AssemblyName AssemblyName=新的AssemblyName();
assemblyName.Name=“tmpAssembly”;
AssemblyBuilder AssemblyBuilder=Thread.GetDomain().DefinedDynamicAssembly(assemblyName,AssemblyBuilderAccess.Run);
ModuleBuilder模块=assemblyBuilder.DefinedDynamicModule(“tmpModule”);
TypeBuilder TypeBuilder=module.DefineType(“WebgridRowCellCollection”,TypeAttributes.Public);
foreach(列表中的字符串步骤)
{
字符串propertyName=步骤;
FieldBuilder field=typeBuilder.DefineField(propertyName、typeof(string)、FieldAttributes.Public);
PropertyBuilder属性=typeBuilder.DefineProperty(propertyName,System.Reflection.PropertyAttributes.None,typeof(string),新类型[]{typeof(string)});
MethodAttributes GetSetAttr=MethodAttributes.Public | MethodAttributes.HideBySig;
MethodBuilder currGetPropMthdBldr=typeBuilder.DefineMethod(“get_值”、GetSetAttr、typeof(字符串)、Type.EmptyTypes);
ILGenerator currGetIL=currGetPropMthdBldr.GetILGenerator();
currGetIL.Emit(操作码.Ldarg_0);
currGetIL.Emit(操作码.Ldfld,字段);
currGetIL.Emit(操作码Ret);
MethodBuilder currSetPropMthdBldr=typeBuilder.DefineMethod(“set_值”,GetSetAttr,null,新类型[]{typeof(string)});
ILGenerator currSetIL=currSetPropMthdBldr.GetILGenerator();
currSetIL.Emit(操作码.Ldarg_0);
currSetIL.Emit(操作码Ldarg_1);
currSetIL.Emit(操作码.Stfld,字段);
currSetIL.Emit(操作码Ret);
SetGetMethod(currGetPropMthdBldr);
属性.SetSetMethod(currSetPropMthdBldr);
}
类型obj=typeBuilder.CreateType();
返回obj;
}
#端区

以前的suneelsarraf代码仅生成属性为字符串的运行时动态对象。 以下更新将根据DataTable列的数据类型生成每个属性

public static class DataTableExtension
{
    /// <summary>
    ///  Convert a database data table to a runtime dynamic definied type collection (dynamic class' name as table name).
    /// </summary>
    /// <param name="dt"></param>
    /// <param name="className"></param>
    /// <returns></returns>
    public static List<dynamic> ToDynamicList(DataTable dt, string className)
    {
        return ToDynamicList(ToDictionary(dt), getNewObject(dt.Columns, className));
    }

    private static List<Dictionary<string, object>> ToDictionary(DataTable dt)
    {
        var columns = dt.Columns.Cast<DataColumn>();
        var Temp = dt.AsEnumerable().Select(dataRow => columns.Select(column =>
                             new { Column = column.ColumnName, Value = dataRow[column] })
                         .ToDictionary(data => data.Column, data => data.Value)).ToList();
        return Temp.ToList();
    }

    private static List<dynamic> ToDynamicList(List<Dictionary<string, object>> list, Type TypeObj)
    {
        dynamic temp = new List<dynamic>();
        foreach (Dictionary<string, object> step in list)
        {
            object Obj = Activator.CreateInstance(TypeObj);

            PropertyInfo[] properties = Obj.GetType().GetProperties();

            Dictionary<string, object> DictList = (Dictionary<string, object>)step;

            foreach (KeyValuePair<string, object> keyValuePair in DictList)
            {
                foreach (PropertyInfo property in properties)
                {
                    if (property.Name == keyValuePair.Key)
                    {
                        if (keyValuePair.Value != null && keyValuePair.Value.GetType() != typeof(System.DBNull))
                        {
                            if (keyValuePair.Value.GetType() == typeof(System.Guid))
                            {
                                property.SetValue(Obj, keyValuePair.Value, null);
                            }
                            else
                            {
                                property.SetValue(Obj, keyValuePair.Value, null);
                            }
                        }
                        break;
                    }
                }
            }
            temp.Add(Obj);
        }
        return temp;
    }

    private static Type getNewObject(DataColumnCollection columns, string className)
    {
        AssemblyName assemblyName = new AssemblyName();
        assemblyName.Name = "YourAssembly";
        System.Reflection.Emit.AssemblyBuilder assemblyBuilder = Thread.GetDomain().DefineDynamicAssembly(assemblyName, AssemblyBuilderAccess.Run);
        ModuleBuilder module = assemblyBuilder.DefineDynamicModule("YourDynamicModule");
        TypeBuilder typeBuilder = module.DefineType(className, TypeAttributes.Public);

        foreach (DataColumn column in columns)
        {
            string propertyName = column.ColumnName;
            FieldBuilder field = typeBuilder.DefineField(propertyName, column.DataType, FieldAttributes.Public);
            PropertyBuilder property = typeBuilder.DefineProperty(propertyName, System.Reflection.PropertyAttributes.None, column.DataType, new Type[] { column.DataType });
            MethodAttributes GetSetAttr = MethodAttributes.Public | MethodAttributes.HideBySig;
            MethodBuilder currGetPropMthdBldr = typeBuilder.DefineMethod("get_value", GetSetAttr, column.DataType, new Type[] { column.DataType }); // Type.EmptyTypes);
            ILGenerator currGetIL = currGetPropMthdBldr.GetILGenerator();
            currGetIL.Emit(OpCodes.Ldarg_0);
            currGetIL.Emit(OpCodes.Ldfld, field);
            currGetIL.Emit(OpCodes.Ret);
            MethodBuilder currSetPropMthdBldr = typeBuilder.DefineMethod("set_value", GetSetAttr, null, new Type[] { column.DataType });
            ILGenerator currSetIL = currSetPropMthdBldr.GetILGenerator();
            currSetIL.Emit(OpCodes.Ldarg_0);
            currSetIL.Emit(OpCodes.Ldarg_1);
            currSetIL.Emit(OpCodes.Stfld, field);
            currSetIL.Emit(OpCodes.Ret);
            property.SetGetMethod(currGetPropMthdBldr);
            property.SetSetMethod(currSetPropMthdBldr);
        }
        Type obj = typeBuilder.CreateType();
        return obj;
    }      
}
公共静态类DataTableExtension
{
/// 
///将数据库数据表转换为运行时动态定义的类型集合(动态类的名称作为表名)。
/// 
/// 
/// 
/// 
公共静态列表到动态列表(数据表dt,字符串类名称)
{
返回到dynamiclist(ToDictionary(dt)、getNewObject(dt.Columns、className));
}
私有静态列表到字典(DataTable dt)
{
var columns=dt.columns.Cast();
var Temp=dt.AsEnumerable().Select(数据行=>columns.Select(列=>
新{Column=Column.ColumnName,Value=dataRow[Column]})
托迪奇先生
public static class DataTableX
{
    public static IEnumerable<dynamic> AsDynamicEnumerable(this DataTable table)
    {
        // Validate argument here..

        return table.AsEnumerable().Select(row => new DynamicRow(row));
    }

    private sealed class DynamicRow : DynamicObject
    {
        private readonly DataRow _row;

        internal DynamicRow(DataRow row) { _row = row; }

        // Interprets a member-access as an indexer-access on the 
        // contained DataRow.
        public override bool TryGetMember(GetMemberBinder binder, out object result)
        {
            var retVal = _row.Table.Columns.Contains(binder.Name);
            result = retVal ? _row[binder.Name] : null;
            return retVal;
        }
    }
}
  DataTable table = ...
  var dynamicTable = table.AsDynamicEnumerable();

  var firstRowsNameField = dynamicTable.First().Name;
    #region "Convert DataTable to List<dynamic>"

    public List<dynamic> ToDynamicList(DataTable dt)
    {
        List<string> cols = (dt.Columns.Cast<DataColumn>()).Select(column => column.ColumnName).ToList();
        return ToDynamicList(ToDictionary(dt), getNewObject(cols));
    }
    public List<Dictionary<string, object>> ToDictionary(DataTable dt)
    {
        var columns = dt.Columns.Cast<DataColumn>();
        var Temp = dt.AsEnumerable().Select(dataRow => columns.Select(column =>
                             new { Column = column.ColumnName, Value = dataRow[column] })
                         .ToDictionary(data => data.Column, data => data.Value)).ToList();
        return Temp.ToList();
    }
    public List<dynamic> ToDynamicList(List<Dictionary<string, object>> list, Type TypeObj)
    {
        dynamic temp = new List<dynamic>();
        foreach (Dictionary<string, object> step in list)
        {
            object Obj = Activator.CreateInstance(TypeObj);
            PropertyInfo[] properties = Obj.GetType().GetProperties();
            Dictionary<string, object> DictList = (Dictionary<string, object>)step;
            foreach (KeyValuePair<string, object> keyValuePair in DictList)
            {
                foreach (PropertyInfo property in properties)
                {
                    if (property.Name == keyValuePair.Key)
                    {
                        property.SetValue(Obj, keyValuePair.Value.ToString(), null);
                        break;
                    }
                }
            }
            temp.Add(Obj);
        }
        return temp;
    }       
    private Type getNewObject(List<string> list)
    {
        AssemblyName assemblyName = new AssemblyName();
        assemblyName.Name = "tmpAssembly";
        AssemblyBuilder assemblyBuilder = Thread.GetDomain().DefineDynamicAssembly(assemblyName, AssemblyBuilderAccess.Run);
        ModuleBuilder module = assemblyBuilder.DefineDynamicModule("tmpModule");
        TypeBuilder typeBuilder = module.DefineType("WebgridRowCellCollection", TypeAttributes.Public);
        foreach (string step in list)
        {
            string propertyName = step;
            FieldBuilder field = typeBuilder.DefineField(propertyName, typeof(string), FieldAttributes.Public);
            PropertyBuilder property = typeBuilder.DefineProperty(propertyName, System.Reflection.PropertyAttributes.None, typeof(string), new Type[] { typeof(string) });
            MethodAttributes GetSetAttr = MethodAttributes.Public | MethodAttributes.HideBySig;
            MethodBuilder currGetPropMthdBldr = typeBuilder.DefineMethod("get_value", GetSetAttr, typeof(string), Type.EmptyTypes);
            ILGenerator currGetIL = currGetPropMthdBldr.GetILGenerator();
            currGetIL.Emit(OpCodes.Ldarg_0);
            currGetIL.Emit(OpCodes.Ldfld, field);
            currGetIL.Emit(OpCodes.Ret);
            MethodBuilder currSetPropMthdBldr = typeBuilder.DefineMethod("set_value", GetSetAttr, null, new Type[] { typeof(string) });
            ILGenerator currSetIL = currSetPropMthdBldr.GetILGenerator();
            currSetIL.Emit(OpCodes.Ldarg_0);
            currSetIL.Emit(OpCodes.Ldarg_1);
            currSetIL.Emit(OpCodes.Stfld, field);
            currSetIL.Emit(OpCodes.Ret);
            property.SetGetMethod(currGetPropMthdBldr);
            property.SetSetMethod(currSetPropMthdBldr);
        }
        Type obj = typeBuilder.CreateType();
        return obj;
    }

    #endregion
public static class DataTableExtension
{
    /// <summary>
    ///  Convert a database data table to a runtime dynamic definied type collection (dynamic class' name as table name).
    /// </summary>
    /// <param name="dt"></param>
    /// <param name="className"></param>
    /// <returns></returns>
    public static List<dynamic> ToDynamicList(DataTable dt, string className)
    {
        return ToDynamicList(ToDictionary(dt), getNewObject(dt.Columns, className));
    }

    private static List<Dictionary<string, object>> ToDictionary(DataTable dt)
    {
        var columns = dt.Columns.Cast<DataColumn>();
        var Temp = dt.AsEnumerable().Select(dataRow => columns.Select(column =>
                             new { Column = column.ColumnName, Value = dataRow[column] })
                         .ToDictionary(data => data.Column, data => data.Value)).ToList();
        return Temp.ToList();
    }

    private static List<dynamic> ToDynamicList(List<Dictionary<string, object>> list, Type TypeObj)
    {
        dynamic temp = new List<dynamic>();
        foreach (Dictionary<string, object> step in list)
        {
            object Obj = Activator.CreateInstance(TypeObj);

            PropertyInfo[] properties = Obj.GetType().GetProperties();

            Dictionary<string, object> DictList = (Dictionary<string, object>)step;

            foreach (KeyValuePair<string, object> keyValuePair in DictList)
            {
                foreach (PropertyInfo property in properties)
                {
                    if (property.Name == keyValuePair.Key)
                    {
                        if (keyValuePair.Value != null && keyValuePair.Value.GetType() != typeof(System.DBNull))
                        {
                            if (keyValuePair.Value.GetType() == typeof(System.Guid))
                            {
                                property.SetValue(Obj, keyValuePair.Value, null);
                            }
                            else
                            {
                                property.SetValue(Obj, keyValuePair.Value, null);
                            }
                        }
                        break;
                    }
                }
            }
            temp.Add(Obj);
        }
        return temp;
    }

    private static Type getNewObject(DataColumnCollection columns, string className)
    {
        AssemblyName assemblyName = new AssemblyName();
        assemblyName.Name = "YourAssembly";
        System.Reflection.Emit.AssemblyBuilder assemblyBuilder = Thread.GetDomain().DefineDynamicAssembly(assemblyName, AssemblyBuilderAccess.Run);
        ModuleBuilder module = assemblyBuilder.DefineDynamicModule("YourDynamicModule");
        TypeBuilder typeBuilder = module.DefineType(className, TypeAttributes.Public);

        foreach (DataColumn column in columns)
        {
            string propertyName = column.ColumnName;
            FieldBuilder field = typeBuilder.DefineField(propertyName, column.DataType, FieldAttributes.Public);
            PropertyBuilder property = typeBuilder.DefineProperty(propertyName, System.Reflection.PropertyAttributes.None, column.DataType, new Type[] { column.DataType });
            MethodAttributes GetSetAttr = MethodAttributes.Public | MethodAttributes.HideBySig;
            MethodBuilder currGetPropMthdBldr = typeBuilder.DefineMethod("get_value", GetSetAttr, column.DataType, new Type[] { column.DataType }); // Type.EmptyTypes);
            ILGenerator currGetIL = currGetPropMthdBldr.GetILGenerator();
            currGetIL.Emit(OpCodes.Ldarg_0);
            currGetIL.Emit(OpCodes.Ldfld, field);
            currGetIL.Emit(OpCodes.Ret);
            MethodBuilder currSetPropMthdBldr = typeBuilder.DefineMethod("set_value", GetSetAttr, null, new Type[] { column.DataType });
            ILGenerator currSetIL = currSetPropMthdBldr.GetILGenerator();
            currSetIL.Emit(OpCodes.Ldarg_0);
            currSetIL.Emit(OpCodes.Ldarg_1);
            currSetIL.Emit(OpCodes.Stfld, field);
            currSetIL.Emit(OpCodes.Ret);
            property.SetGetMethod(currGetPropMthdBldr);
            property.SetSetMethod(currSetPropMthdBldr);
        }
        Type obj = typeBuilder.CreateType();
        return obj;
    }      
}
using System;
using System.Collections.Generic;
using System.Data;
using System.Dynamic;

public static class DataTableExtensions
{
    public static IEnumerable<dynamic> AsDynamicEnumerable(this DataTable table)
    {
        if (table == null)
        {
            yield break;
        }

        foreach (DataRow row in table.Rows)
        {
            IDictionary<string, object> dRow = new ExpandoObject();

            foreach (DataColumn column in table.Columns)
            {
                var value = row[column.ColumnName];
                dRow[column.ColumnName] = Convert.IsDBNull(value) ? null : value;
            }

            yield return dRow;
        }
    }
}
var dataTable = GetDataTableFromSomewhere();
var dynamicTable = dataTable.AsDynamicEnumerable();
var firstRowIDColumn = dynamicTable.First().ID;
var lastRowIDColumn = dynamicTable.Last()["ID"];