├── TransformDTAndModel ├── TransformDTToModel.v12.suo ├── Properties │ └── AssemblyInfo.cs ├── TransformDTAndModel.csproj └── TransformUtil.cs ├── UnitTest ├── People.cs ├── Properties │ └── AssemblyInfo.cs ├── UnitTestForTransformDTAndModel.cs └── UnitTest.csproj ├── .gitignore └── TransformDTAndModel.sln /TransformDTAndModel/TransformDTToModel.v12.suo: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/sinodzh/TransformDTAndModel/HEAD/TransformDTAndModel/TransformDTToModel.v12.suo -------------------------------------------------------------------------------- /UnitTest/People.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using System.Linq; 4 | using System.Text; 5 | 6 | namespace UnitTest 7 | { 8 | public class People 9 | { 10 | public string Id { get; set; } 11 | 12 | public string Name { get; set; } 13 | 14 | public string Address { get; set; } 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /UnitTest/Properties/AssemblyInfo.cs: -------------------------------------------------------------------------------- 1 | using System.Reflection; 2 | using System.Runtime.CompilerServices; 3 | using System.Runtime.InteropServices; 4 | 5 | // 有关程序集的常规信息通过以下特性集 6 | // 控制。更改这些特性值可修改 7 | // 与程序集关联的信息。 8 | [assembly: AssemblyTitle("UnitTest")] 9 | [assembly: AssemblyDescription("")] 10 | [assembly: AssemblyConfiguration("")] 11 | [assembly: AssemblyCompany("china")] 12 | [assembly: AssemblyProduct("UnitTest")] 13 | [assembly: AssemblyCopyright("Copyright © china 2015")] 14 | [assembly: AssemblyTrademark("")] 15 | [assembly: AssemblyCulture("")] 16 | 17 | // 将 ComVisible 设置为 false 会使此程序集中的类型 18 | // 对 COM 组件不可见。 如果需要从 COM 访问此程序集中的类型, 19 | // 请将该类型上的 ComVisible 特性设置为 true。 20 | [assembly: ComVisible(false)] 21 | 22 | // 如果此项目向 COM 公开,则下列 GUID 用于类型库的 ID 23 | [assembly: Guid("489b42be-6756-4224-a955-8545ec9e95f8")] 24 | 25 | // 程序集的版本信息由以下四个值组成: 26 | // 27 | // 主版本 28 | // 次版本 29 | // 生成号 30 | // 修订号 31 | // 32 | // 可以指定所有这些值,也可以使用“生成号”和“修订号”的默认值, 33 | // 方法是按如下所示使用“*”: 34 | // [assembly: AssemblyVersion("1.0.*")] 35 | [assembly: AssemblyVersion("1.0.0.0")] 36 | [assembly: AssemblyFileVersion("1.0.0.0")] 37 | -------------------------------------------------------------------------------- /TransformDTAndModel/Properties/AssemblyInfo.cs: -------------------------------------------------------------------------------- 1 | using System.Reflection; 2 | using System.Runtime.CompilerServices; 3 | using System.Runtime.InteropServices; 4 | 5 | // 有关程序集的常规信息通过以下 6 | // 特性集控制。更改这些特性值可修改 7 | // 与程序集关联的信息。 8 | [assembly: AssemblyTitle("TransformDTAndModel")] 9 | [assembly: AssemblyDescription("")] 10 | [assembly: AssemblyConfiguration("")] 11 | [assembly: AssemblyCompany("china")] 12 | [assembly: AssemblyProduct("TransformDTAndModel")] 13 | [assembly: AssemblyCopyright("Copyright © china 2015")] 14 | [assembly: AssemblyTrademark("")] 15 | [assembly: AssemblyCulture("")] 16 | 17 | // 将 ComVisible 设置为 false 使此程序集中的类型 18 | // 对 COM 组件不可见。 如果需要从 COM 访问此程序集中的类型, 19 | // 则将该类型上的 ComVisible 特性设置为 true。 20 | [assembly: ComVisible(false)] 21 | 22 | // 如果此项目向 COM 公开,则下列 GUID 用于类型库的 ID 23 | [assembly: Guid("8cb4470d-6c83-48c2-b0d0-c7342191d35c")] 24 | 25 | // 程序集的版本信息由下面四个值组成: 26 | // 27 | // 主版本 28 | // 次版本 29 | // 生成号 30 | // 修订号 31 | // 32 | // 可以指定所有这些值,也可以使用“生成号”和“修订号”的默认值, 33 | // 方法是按如下所示使用“*”: 34 | // [assembly: AssemblyVersion("1.0.*")] 35 | [assembly: AssemblyVersion("1.0.0.0")] 36 | [assembly: AssemblyFileVersion("1.0.0.0")] 37 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | ################################################################################ 2 | # 此 .gitignore 文件已由 Microsoft(R) Visual Studio 自动创建。 3 | ################################################################################ 4 | 5 | /TransformDTAndModel/bin/Debug/TransformDTAndModel.dll 6 | /TransformDTAndModel/bin/Debug/TransformDTAndModel.pdb 7 | /TransformDTAndModel/bin/Debug/TransformDTToModel.dll 8 | /TransformDTAndModel/bin/Debug/TransformDTToModel.pdb 9 | /TransformDTAndModel/obj/Debug/DesignTimeResolveAssemblyReferencesInput.cache 10 | /TransformDTAndModel/obj/Debug/TransformDTAndModel.csproj.FileListAbsolute.txt 11 | /TransformDTAndModel/obj/Debug/TransformDTAndModel.csprojResolveAssemblyReference.cache 12 | /TransformDTAndModel/obj/Debug/TransformDTAndModel.dll 13 | /TransformDTAndModel/obj/Debug/TransformDTAndModel.pdb 14 | /TransformDTAndModel/obj/Debug/TransformDTToModel.csproj.FileListAbsolute.txt 15 | /TransformDTAndModel/obj/Debug/TransformDTToModel.csprojResolveAssemblyReference.cache 16 | /TransformDTAndModel/obj/Debug/TransformDTToModel.dll 17 | /TransformDTAndModel/obj/Debug/TransformDTToModel.pdb 18 | /UnitTest/bin/Debug/TransformDTAndModel.dll 19 | /UnitTest/bin/Debug/TransformDTAndModel.pdb 20 | /UnitTest/bin/Debug/UnitTest.dll 21 | /UnitTest/bin/Debug/UnitTest.pdb 22 | /UnitTest/obj/Debug/DesignTimeResolveAssemblyReferencesInput.cache 23 | /UnitTest/obj/Debug/UnitTest.csproj.FileListAbsolute.txt 24 | /UnitTest/obj/Debug/UnitTest.csprojResolveAssemblyReference.cache 25 | /UnitTest/obj/Debug/UnitTest.dll 26 | /UnitTest/obj/Debug/UnitTest.pdb 27 | -------------------------------------------------------------------------------- /TransformDTAndModel.sln: -------------------------------------------------------------------------------- 1 | 2 | Microsoft Visual Studio Solution File, Format Version 12.00 3 | # Visual Studio 2013 4 | VisualStudioVersion = 12.0.21005.1 5 | MinimumVisualStudioVersion = 10.0.40219.1 6 | Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "TransformDTAndModel", "TransformDTAndModel\TransformDTAndModel.csproj", "{464B57DA-2A2B-4C44-9BFA-E4C48E316374}" 7 | EndProject 8 | Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "UnitTest", "UnitTest\UnitTest.csproj", "{6F4E3A57-4C41-456F-832E-D1A9A4B074D8}" 9 | EndProject 10 | Global 11 | GlobalSection(SolutionConfigurationPlatforms) = preSolution 12 | Debug|Any CPU = Debug|Any CPU 13 | Release|Any CPU = Release|Any CPU 14 | EndGlobalSection 15 | GlobalSection(ProjectConfigurationPlatforms) = postSolution 16 | {464B57DA-2A2B-4C44-9BFA-E4C48E316374}.Debug|Any CPU.ActiveCfg = Debug|Any CPU 17 | {464B57DA-2A2B-4C44-9BFA-E4C48E316374}.Debug|Any CPU.Build.0 = Debug|Any CPU 18 | {464B57DA-2A2B-4C44-9BFA-E4C48E316374}.Release|Any CPU.ActiveCfg = Release|Any CPU 19 | {464B57DA-2A2B-4C44-9BFA-E4C48E316374}.Release|Any CPU.Build.0 = Release|Any CPU 20 | {6F4E3A57-4C41-456F-832E-D1A9A4B074D8}.Debug|Any CPU.ActiveCfg = Debug|Any CPU 21 | {6F4E3A57-4C41-456F-832E-D1A9A4B074D8}.Debug|Any CPU.Build.0 = Debug|Any CPU 22 | {6F4E3A57-4C41-456F-832E-D1A9A4B074D8}.Release|Any CPU.ActiveCfg = Release|Any CPU 23 | {6F4E3A57-4C41-456F-832E-D1A9A4B074D8}.Release|Any CPU.Build.0 = Release|Any CPU 24 | EndGlobalSection 25 | GlobalSection(SolutionProperties) = preSolution 26 | HideSolutionNode = FALSE 27 | EndGlobalSection 28 | EndGlobal 29 | -------------------------------------------------------------------------------- /UnitTest/UnitTestForTransformDTAndModel.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using Microsoft.VisualStudio.TestTools.UnitTesting; 3 | using TransformDTToModel; 4 | using System.Data; 5 | using System.Collections.Generic; 6 | 7 | namespace UnitTest 8 | { 9 | [TestClass] 10 | public class UnitTestForTransformDTAndModel 11 | { 12 | [TestMethod] 13 | public void TestConvertDataTableToModel() 14 | { 15 | DataTable dt = new DataTable(); 16 | dt.Columns.Add("Id", typeof(string)); 17 | dt.Columns.Add("Name", typeof(string)); 18 | dt.Columns.Add("Address", typeof(string)); 19 | dt.PrimaryKey = new DataColumn[] { dt.Columns[0] }; 20 | 21 | dt.Rows.Add("0001", "张三", "武汉市"); 22 | dt.Rows.Add("0002", "李四", "北京市"); 23 | dt.AcceptChanges(); 24 | dt.Rows.Add("0003", "王五", "深圳市"); 25 | 26 | List allPeople = new List(); 27 | 28 | TransformUtil.ConvertDataTableToModel(dt, allPeople); 29 | 30 | //断言是不是只有一个数据,平且是只是修改状态的王五这个人 31 | Assert.AreEqual(allPeople.Count, 1); 32 | Assert.AreEqual(allPeople[0].Name, "王五"); 33 | } 34 | 35 | [TestMethod] 36 | public void TestConvertModelToDataTable() 37 | { 38 | List allPeople = new List() 39 | { 40 | new People(){ Id="0001", Name="张三", Address ="武汉市"}, 41 | new People(){ Id="0002", Name="李四", Address ="北京市"}, 42 | new People(){ Id="0003", Name="王五", Address ="深圳市"} 43 | }; 44 | 45 | DataTable dt = TransformUtil.ConvertModelToDataTable(allPeople, null); 46 | 47 | 48 | //断言是不是有3行数据,数据的列有3列,第1列是不是Id,第一行第二列是不是张三 49 | Assert.AreEqual(dt.Rows.Count, 3); 50 | Assert.AreEqual(dt.Columns.Count, 3); 51 | Assert.AreEqual(dt.Columns[0].ColumnName, "Id"); 52 | Assert.AreEqual(dt.Rows[0][1], "张三"); 53 | } 54 | } 55 | } 56 | -------------------------------------------------------------------------------- /TransformDTAndModel/TransformDTAndModel.csproj: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | Debug 6 | AnyCPU 7 | {464B57DA-2A2B-4C44-9BFA-E4C48E316374} 8 | Library 9 | Properties 10 | TransformDTAndModel 11 | TransformDTAndModel 12 | v4.0 13 | 512 14 | 15 | 16 | true 17 | full 18 | false 19 | bin\Debug\ 20 | DEBUG;TRACE 21 | prompt 22 | 4 23 | 24 | 25 | pdbonly 26 | true 27 | bin\Release\ 28 | TRACE 29 | prompt 30 | 4 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 53 | -------------------------------------------------------------------------------- /UnitTest/UnitTest.csproj: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | Debug 5 | AnyCPU 6 | {6F4E3A57-4C41-456F-832E-D1A9A4B074D8} 7 | Library 8 | Properties 9 | UnitTest 10 | UnitTest 11 | v4.0 12 | 512 13 | {3AC096D0-A1C2-E12C-1390-A8335801FDAB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} 14 | 10.0 15 | $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) 16 | $(ProgramFiles)\Common Files\microsoft shared\VSTT\$(VisualStudioVersion)\UITestExtensionPackages 17 | False 18 | UnitTest 19 | 20 | 21 | true 22 | full 23 | false 24 | bin\Debug\ 25 | DEBUG;TRACE 26 | prompt 27 | 4 28 | 29 | 30 | pdbonly 31 | true 32 | bin\Release\ 33 | TRACE 34 | prompt 35 | 4 36 | 37 | 38 | 39 | 40 | 3.5 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | {464b57da-2a2b-4c44-9bfa-e4c48e316374} 65 | TransformDTAndModel 66 | 67 | 68 | 69 | 70 | 71 | 72 | False 73 | 74 | 75 | False 76 | 77 | 78 | False 79 | 80 | 81 | False 82 | 83 | 84 | 85 | 86 | 87 | 88 | 95 | -------------------------------------------------------------------------------- /TransformDTAndModel/TransformUtil.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections; 3 | using System.Collections.Generic; 4 | using System.Data; 5 | using System.Linq; 6 | using System.Reflection; 7 | using System.Text; 8 | 9 | namespace TransformDTToModel 10 | { 11 | public class TransformUtil 12 | { 13 | /// 14 | /// 将DB中改动的内容同步到泛型集合中 15 | /// 16 | /// 类型 17 | /// dt源 18 | /// 目标Model集合 19 | /// 20 | public static bool ConvertDataTableToModel(DataTable source, List destinationArray) 21 | where T : class 22 | { 23 | if (source == null || destinationArray == null || source.PrimaryKey == null || source.PrimaryKey.Count() <= 0) 24 | return false; 25 | 26 | DataTable dtChange = source.GetChanges(); 27 | if (dtChange == null) 28 | return false; 29 | 30 | List keys = new List(); 31 | foreach (var item in source.PrimaryKey) 32 | { 33 | keys.Add(item.ColumnName); 34 | } 35 | 36 | return ConvertDataTableToModel(source, destinationArray, keys); 37 | } 38 | 39 | /// 40 | /// 同步table里改动的数据到泛型集合里去(新增,修改,删除) 41 | /// 42 | /// 类型 43 | /// dt源 44 | /// 目标Model集合 45 | /// 主键集合 46 | /// 47 | public static bool ConvertDataTableToModel(DataTable source, List destinationArray, List keyColumnArray) 48 | where T : class 49 | { 50 | if (source == null || destinationArray == null || source.Rows.Count == 0 || keyColumnArray == null || keyColumnArray.Count == 0) 51 | return false; 52 | 53 | Type modeType = destinationArray.GetType().GetGenericArguments()[0];//模型类型 54 | PropertyInfo[] ppInfoArray = modeType.GetProperties();//公共属性集合 55 | List listPPInfo = ppInfoArray.ToList();//方便查询 56 | //关键列 57 | List keyPIArray = listPPInfo.FindAll(x => keyColumnArray.Contains(x.Name)); 58 | 59 | List listToDelete = new List(); 60 | //新增的数据 61 | DataRow[] drAddArray = source.Select("", "", DataViewRowState.Added); 62 | 63 | object objItem = modeType.Assembly.CreateInstance(modeType.FullName); 64 | foreach (DataRow dr in drAddArray) 65 | { 66 | destinationArray.Add((T)objItem); 67 | foreach (System.Reflection.PropertyInfo pi in listPPInfo) 68 | { 69 | pi.SetValue(destinationArray[destinationArray.Count - 1], dr[pi.Name], null); 70 | } 71 | } 72 | //修改和删除的数据 73 | DataView dvForOP = new DataView(source); 74 | dvForOP.RowStateFilter = DataViewRowState.Deleted | DataViewRowState.ModifiedCurrent; 75 | 76 | foreach (DataRowView drv in dvForOP) 77 | { 78 | for (int i = 0; i < destinationArray.Count; i++) 79 | { 80 | bool blIsTheRow = true; 81 | //找出关键列对应的行 82 | foreach (System.Reflection.PropertyInfo pInfo in keyPIArray) 83 | { 84 | object okey = pInfo.GetValue(destinationArray[i], null); 85 | if (okey == null) 86 | continue; 87 | if (drv[pInfo.Name].ToString() != okey.ToString()) 88 | { 89 | blIsTheRow = false; 90 | break; 91 | } 92 | } 93 | if (!blIsTheRow)//非本行 94 | continue; 95 | //根据行状态同步赋值 96 | switch (drv.Row.RowState) 97 | { 98 | case DataRowState.Modified: 99 | { 100 | foreach (System.Reflection.PropertyInfo pi in listPPInfo) 101 | { 102 | if (keyPIArray.Contains(pi))//主键列不更新 103 | continue; 104 | pi.SetValue(destinationArray[i], drv[pi.Name], null); 105 | } 106 | } break; 107 | case DataRowState.Deleted: 108 | { 109 | listToDelete.Add(destinationArray[i]); 110 | } break; 111 | } 112 | } 113 | } 114 | 115 | for (int i = 0; i < listToDelete.Count; i++) 116 | { 117 | destinationArray.Remove(listToDelete[i]); 118 | } 119 | 120 | return true; 121 | } 122 | 123 | /// 124 | /// 将视图转换成泛型集合 125 | /// 126 | /// 类型 127 | /// 视图 128 | /// 泛型实例 129 | /// 130 | public static List ConvertDataViewToModel(DataView dataView, T model) 131 | where T:class 132 | { 133 | List listReturn = new List(); 134 | Type modelType = model.GetType(); 135 | DataTable dt = dataView.Table; 136 | //获取model所有类型 137 | PropertyInfo[] modelProperties = modelType.GetProperties(); 138 | 139 | //遍历所有行,逐行添加对象 140 | for (int i = 0; i < dt.Rows.Count; i++) 141 | { 142 | object obj = modelType.Assembly.CreateInstance(modelType.FullName); 143 | listReturn.Add((T)obj); 144 | //遍历model所有属性 145 | foreach (PropertyInfo pi in modelProperties) 146 | { 147 | //遍历所有列 148 | foreach (DataColumn col in dt.Columns) 149 | { 150 | //如果列数据类型与model的数据类型相同、名称相同 151 | if (col.DataType == pi.PropertyType 152 | && col.ColumnName == pi.Name) 153 | { 154 | pi.SetValue(obj, dt.Rows[i][col.ColumnName], null); 155 | } 156 | } 157 | } 158 | } 159 | 160 | return listReturn; 161 | } 162 | 163 | /// 164 | /// 将泛型集合类转换成DataTable 165 | /// 166 | /// 集合项类型 167 | /// 集合 168 | /// 需要返回的列的列名,如需返回所有列,此参数传入null值 169 | /// 数据集(表) 170 | public static DataTable ConvertModelToDataTable(IList sourceArray, params string[] propertyNameArray) 171 | where T:class 172 | { 173 | List propertyNameList = new List(); 174 | if (propertyNameArray != null) 175 | propertyNameList.AddRange(propertyNameArray); 176 | 177 | DataTable result = new DataTable(); 178 | //获取结构 179 | Type[] typeArr = sourceArray.GetType().GetGenericArguments(); 180 | if (typeArr.Length == 0) 181 | return result; 182 | 183 | PropertyInfo[] propertys = typeArr[0].GetProperties(); 184 | foreach (PropertyInfo pi in propertys) 185 | { 186 | if (propertyNameList.Count == 0) 187 | { 188 | result.Columns.Add(pi.Name, pi.PropertyType); 189 | } 190 | else 191 | { 192 | if (propertyNameList.Contains(pi.Name)) 193 | result.Columns.Add(pi.Name, pi.PropertyType); 194 | } 195 | } 196 | for (int i = 0; i < sourceArray.Count; i++) 197 | { 198 | ArrayList tempList = new ArrayList(); 199 | foreach (PropertyInfo pi in propertys) 200 | { 201 | if (propertyNameList.Count == 0) 202 | { 203 | object obj = pi.GetValue(sourceArray[i], null); 204 | tempList.Add(obj); 205 | } 206 | else 207 | { 208 | if (propertyNameList.Contains(pi.Name)) 209 | { 210 | object obj = pi.GetValue(sourceArray[i], null); 211 | tempList.Add(obj); 212 | } 213 | } 214 | } 215 | object[] array = tempList.ToArray(); 216 | result.LoadDataRow(array, true); 217 | } 218 | 219 | return result; 220 | } 221 | 222 | } 223 | } 224 | --------------------------------------------------------------------------------