C#类两种动态添加属性并赋值的解决方法
搜索网上资料并根据项目中的需要最终整理出来分享给大家,希望对大家有所帮助
功能:将DataTable 中的colums名称作为属性动态添加到类中,将DataTable中的第一行数据给属性赋值
1.第一种方法 使用Dynamic 支持.net4.0以上版本支持
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
/// <summary> /// 使用dynamic根据DataTable的列名自动添加属性并赋值 /// </summary> /// <param name="dt"></param> /// <returns></returns> public static Object GetDynamicClassBydt(DataTable dt) { dynamic d = new System.Dynamic.ExpandoObject(); //创建属性,并赋值。 foreach (DataColumn cl in dt.Columns) { (d as System.Collections.Generic.ICollection<System.Collections.Generic.KeyValuePair<string, object>>).Add(newSystem.Collections.Generic.KeyValuePair<string, object>(cl.ColumnName, dt.Rows[0][cl.ColumnName].ToString())); } return d; }
2.第二种方法 使用反射(此方法比方法一的性能低,是通过动态生成类、并动态生成类的属性)
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
/// <summary> /// 使用反射 动态创建类,将DataTable的列名动态添加为该类的属性,并给属性赋值 /// 该方法由于要动态创建类,性能比较低(注意只是将DataTable的第一行转换为动态实体类) /// </summary> /// <param name="dt"></param> /// <returns></returns> public static Object CreatNewClassBydt(DataTable dt) { if (dt == null || dt.Rows.Count < 1) { return null; } //创建编译器实例。 CSharpCodeProvider provider = new CSharpCodeProvider(); //设置编译参数。 CompilerParameters paras = new CompilerParameters(); paras.GenerateExecutable = false; paras.GenerateInMemory = true; //创建动态代码。 StringBuilder classSource = new StringBuilder(); classSource.Append("public class DynamicClass \n"); classSource.Append("{\n"); //创建属性。 foreach (DataColumn cl in dt.Columns) { classSource.Append(propertyString(cl.ColumnName)); } classSource.Append("}"); System.Diagnostics.Debug.WriteLine(classSource.ToString()); //编译代码。 CompilerResults result = provider.CompileAssemblyFromSource(paras, classSource.ToString()); //获取编译后的程序集。 Assembly assembly = result.CompiledAssembly; object obclass = assembly.CreateInstance("DynamicClass"); foreach (DataColumn cl in dt.Columns) { ReflectionSetProperty(obclass, cl.ColumnName, dt.Rows[0][cl.ColumnName].ToString()); PropertyInfo _Property = obclass.GetType().GetProperty(cl.ColumnName); if (_Property != null && _Property.CanRead) { _Property.SetValue(obclass, dt.Rows[0][cl.ColumnName].ToString(), null); } } return obclass; }