C#代码实现 Excel表格与Object互相转换,Excel表格导入数据库(.NET2.0 .NET4.0)

前些天在工作上遇到这个需求,在GitHub找到一个开源代码可以用,Fork了一个版本,整理一下发出来。

①.Net项目中使用Nuget安装一个 NPOI 包    https://github.com/tonyqus/npoi

再Nuget安装 Chsword.Excel2Object 包    https://github.com/chsword/Excel2Object

 也可以直接使用命令行(“Install-Package Chsword.Excel2Object”

注:上述程序包是作者的源代码,如果项目的.NET版本太低(2.0神马的),比如我们╮(╯▽╰)╭ ,可以跳过此步骤直接复制下面的代码。

   我把.NET4.0的语法都替换掉了,用到的类都揉到一个页面了,没有作者那么条理清晰,引用方便一些。

  1 using System;
  2 using System.Collections;
  3 using System.Collections.Generic;
  4 using System.IO;
  5 using System.Reflection;
  6 using NPOI.HSSF.UserModel;
  7 using NPOI.SS.UserModel;
  8
  9
 10 namespace Bu.Function
 11 {
 12
 13     /// <summary>
 14     /// excel转object
 15     /// </summary>
 16
 17     public class ExcelAttribute : Attribute
 18     {
 19         public ExcelAttribute(string name)
 20         {
 21             Title = name;
 22         }
 23
 24         public int Order { get; set; }
 25         public string Title { get; set; }
 26     }
 27
 28
 29     public class ExcelImporter
 30     {
 31         public IEnumerable<TModel> ExcelToObject<TModel>(string path, int? type = null) where TModel : class, new()
 32         {
 33             var result = GetDataRows(path);
 34             var dict = ExcelUtil.GetExportAttrDict<TModel>();
 35             var dictColumns = new Dictionary<int, KeyValuePair<PropertyInfo, ExcelAttribute>>();
 36
 37             IEnumerator rows = result;
 38
 39             var titleRow = (IRow)rows.Current;
 40             if (titleRow != null)
 41                 foreach (var cell in titleRow.Cells)
 42                 {
 43                     var prop = new KeyValuePair<PropertyInfo, ExcelAttribute>();
 44                     foreach (var item in dict)
 45                     {
 46                         if (cell.StringCellValue == item.Value.Title)
 47                         {
 48                             prop = item;
 49                         }
 50                     }
 51
 52                     if (prop.Key != null && !dictColumns.ContainsKey(cell.ColumnIndex))
 53                     {
 54                         dictColumns.Add(cell.ColumnIndex, prop);
 55                     }
 56                 }
 57             while (rows.MoveNext())
 58             {
 59                 var row = (IRow)rows.Current;
 60                 if (row != null)
 61                 {
 62                     var firstCell = row.GetCell(0);
 63                     if (firstCell == null || firstCell.CellType == CellType.Blank ||
 64                         string.IsNullOrEmpty(firstCell.ToString()))
 65                         continue;
 66                 }
 67
 68                 var model = new TModel();
 69
 70                 foreach (var pair in dictColumns)
 71                 {
 72                     var propType = pair.Value.Key.PropertyType;
 73                     if (propType == typeof(DateTime?) ||
 74                         propType == typeof(DateTime))
 75                     {
 76                         pair.Value.Key.SetValue(model, GetCellDateTime(row, pair.Key), null);
 77                     }
 78                     else
 79                     {
 80
 81                         try
 82                         {
 83                             var  val= Convert.ChangeType(GetCellValue(row, pair.Key), propType);
 84                             pair.Value.Key.SetValue(model, val, null);
 85                         }
 86                         catch (Exception ex)
 87                         {
 88                             break;
 89                         }
 90
 91
 92                     }
 93                 }
 94                 yield return model;
 95             }
 96
 97         }
 98
 99         string GetCellValue(IRow row, int index)
100         {
101             var result = string.Empty;
102             try
103             {
104                 switch (row.GetCell(index).CellType)
105                 {
106                     case CellType.Numeric:
107                         result = row.GetCell(index).NumericCellValue.ToString();
108                         break;
109                     case CellType.String:
110                         result = row.GetCell(index).StringCellValue;
111                         break;
112                     case CellType.Blank:
113                         result = string.Empty;
114                         break;
115
116                     #region
117
118                     //case CellType.Formula:
119                     //    result = row.GetCell(index).CellFormula;
120                     //    break;
121                     //case CellType.Boolean:
122                     //    result = row.GetCell(index).NumericCellValue.ToString();
123                     //    break;
124                     //case CellType.Error:
125                     //    result = row.GetCell(index).NumericCellValue.ToString();
126                     //    break;
127                     //case CellType.Unknown:
128                     //    result = row.GetCell(index).NumericCellValue.ToString();
129                     //    break;
130
131                     #endregion
132                     default:
133                         result = row.GetCell(index).ToString();
134                         break;
135                 }
136             }
137             catch (Exception e)
138             {
139                 Console.WriteLine(e);
140             }
141             return (result ?? "").Trim();
142         }
143         IEnumerator GetDataRows(string path)
144         {
145             if (string.IsNullOrEmpty(path))
146                 return null;
147             HSSFWorkbook hssfworkbook;
148             try
149             {
150                 using (FileStream file = new FileStream(path, FileMode.Open, FileAccess.Read))
151                 {
152                     hssfworkbook = new HSSFWorkbook(file);
153                 }
154             }
155             catch (Exception)
156             {
157                 return null;
158             }
159             ISheet sheet = hssfworkbook.GetSheetAt(0);
160             IEnumerator rows = sheet.GetRowEnumerator();
161             rows.MoveNext();
162             return rows;
163         }
164
165         DateTime? GetCellDateTime(IRow row, int index)
166         {
167             DateTime? result = null;
168             try
169             {
170                 switch (row.GetCell(index).CellType)
171                 {
172                     case CellType.Numeric:
173                         try
174                         {
175                             result = row.GetCell(index).DateCellValue;
176                         }
177                         catch (Exception e)
178                         {
179                             Console.WriteLine(e);
180                         }
181                         break;
182                     case CellType.String:
183                         var str = row.GetCell(index).StringCellValue;
184                         if (str.EndsWith("年"))
185                         {
186                             DateTime dt;
187                             if (DateTime.TryParse((str + "-01-01").Replace("年", ""), out dt))
188                             {
189                                 result = dt;
190                             }
191                         }
192                         else if (str.EndsWith("月"))
193                         {
194                             DateTime dt;
195                             if (DateTime.TryParse((str + "-01").Replace("年", "").Replace("月", ""), out dt))
196                             {
197                                 result = dt;
198                             }
199                         }
200                         else if (!str.Contains("年") && !str.Contains("月") && !str.Contains("日"))
201                         {
202                             try
203                             {
204                                 result = Convert.ToDateTime(str);
205                             }
206                             catch (Exception)
207                             {
208                                 try
209                                 {
210                                     result = Convert.ToDateTime((str + "-01-01").Replace("年", "").Replace("月", ""));
211                                 }
212                                 catch (Exception)
213                                 {
214                                     result = null;
215                                 }
216                             }
217                         }
218                         else
219                         {
220                             DateTime dt;
221                             if (DateTime.TryParse(str.Replace("年", "").Replace("月", ""), out dt))
222                             {
223                                 result = dt;
224                             }
225                         }
226                         break;
227                     case CellType.Blank:
228                         break;
229                     #region
230
231                     #endregion
232                 }
233             }
234             catch (Exception e)
235             {
236                 Console.WriteLine(e);
237             }
238             return result;
239         }
240     }
241
242
243     class ExcelExporter
244     {
245         public byte[] ObjectToExcelBytes<TModel>(IEnumerable<TModel> data)
246         {
247             var workbook = new HSSFWorkbook();
248             var sheet = workbook.CreateSheet();
249             var attrDict = ExcelUtil.GetExportAttrDict<TModel>();
250             var attrArray = new KeyValuePair<PropertyInfo, ExcelAttribute>[] { };
251             int aNum = 0;
252             foreach (var item in attrDict)
253             {
254                 attrArray[aNum] = item;
255                 aNum++;
256
257             }
258
259             for (int i = 0; i < attrArray.Length; i++)
260             {
261                 sheet.SetColumnWidth(i, 50 * 256);
262             }
263             var headerRow = sheet.CreateRow(0);
264
265             for (int i = 0; i < attrArray.Length; i++)
266             {
267                 headerRow.CreateCell(i).SetCellValue(attrArray[i].Value.Title);
268             }
269             int rowNumber = 1;
270             foreach (var item in data)
271             {
272                 var row = sheet.CreateRow(rowNumber++);
273                 for (int i = 0; i < attrArray.Length; i++)
274                 {
275                     row.CreateCell(i).SetCellValue((attrArray[i].Key.GetValue(item, null) ?? "").ToString());
276                 }
277             }
278             using (var output = new MemoryStream())
279             {
280                 workbook.Write(output);
281                 var bytes = output.ToArray();
282                 return bytes;
283             }
284         }
285
286
287     }
288
289
290
291
292     public class ExcelHelper
293     {
294         /// <summary>
295         /// import file excel file to a IEnumerable of TModel
296         /// </summary>
297         /// <typeparam name="TModel"></typeparam>
298         /// <param name="path">excel full path</param>
299         /// <returns></returns>
300         public static IEnumerable<TModel> ExcelToObject<TModel>(string path) where TModel : class, new()
301         {
302             var importer = new ExcelImporter();
303             return importer.ExcelToObject<TModel>(path);
304
305         }
306
307         /// <summary>
308         /// Export object to excel file
309         /// </summary>
310         /// <typeparam name="TModel"></typeparam>
311         /// <param name="data">a IEnumerable of TModel</param>
312         /// <param name="path">excel full path</param>
313         public static void ObjectToExcel<TModel>(IEnumerable<TModel> data, string path) where TModel : class, new()
314         {
315             var importer = new ExcelExporter();
316             var bytes = importer.ObjectToExcelBytes(data);
317             File.WriteAllBytes(path, bytes);
318         }
319     }
320
321
322     internal class ExcelUtil
323     {
324         public static Dictionary<PropertyInfo, ExcelAttribute> GetExportAttrDict<T>()
325         {
326             var dict = new Dictionary<PropertyInfo, ExcelAttribute>();
327             foreach (var propertyInfo in typeof(T).GetProperties())
328             {
329                 var attr = new object();
330                 var ppi = propertyInfo.GetCustomAttributes(true);
331                 for (int i = 0; i < ppi.Length; i++)
332                 {
333                     if (ppi[i] is ExcelAttribute)
334                     {
335                         attr = ppi[i];
336                         break;
337                     }
338                 }
339
340                 if (attr != null)
341                 {
342
343                     dict.Add(propertyInfo, attr as ExcelAttribute);
344
345                 }
346             }
347             return dict;
348         }
349     }
350
351
352
353
354 }

准备一段 Demo Code

public class ReportModel
{
    [Excel("标题",Order=1)]
    public string Title { get; set; }
    [Excel("用户",Order=2)]
    public string Name { get; set; }
}

准备一个List

 var models = new List<ReportModel>
        {
            new ReportModel{Name="a",Title="b"},
            new ReportModel{Name="c",Title="d"},
            new ReportModel{Name="f",Title="e"}
        };

由Object转为Excel

var exporter = new ExcelExporter();
  var bytes = exporter.ObjectToExcelBytes(models);
  File.WriteAllBytes("C:\\demo.xls", bytes);

由Excel转为Object

var importer = new ExcelImporter();
  IEnumerable<ReportModel> result = importer.ExcelToObject<ReportModel>("c:\\demo.xls");

转成Object再验证,存入数据库神马的 是不是就so easy啦~



与ASP.NET MVC结合使用

由于ASP.NET MVC中Model上会使用DisplayAttribute所以Excel2Object除了支持ExcelAttribute外,也支持DisplayAttribute。

C#代码实现 Excel表格与Object互相转换,Excel表格导入数据库(.NET2.0 .NET4.0)

时间: 2024-10-25 19:39:13

C#代码实现 Excel表格与Object互相转换,Excel表格导入数据库(.NET2.0 .NET4.0)的相关文章

excel转pdf,itextpdf转换excel

最近项目有需求,需要把excel转pdf.由于时间比较急,所以在github上找了一个转换的.最终没用上,但还是踩坑了一波. 踩坑一: 首先,这个是导出的流之间会互相影响,因为流读取过,导致导出的excle文件没有数据,所以要new 新的流 踩坑二: github上找的excel转pdf工具类,本来以为挺简单的.大意了,搞了很久发现工具类有问题,项目还着急提测.导致我被pm说了一波. 原工具类地址:https://github.com/caryyu/excel2pdf 我完善过的工具类:http

excel十几万行数据快速导入数据库研究(转,下面那个方法看看还是可以的)

先贴原来的导入数据代码: 8 import os os.environ.setdefault("DJANGO_SETTINGS_MODULE", "www.settings") ''' Django 版本大于等于1.7的时候,需要加上下面两句 import django django.setup() 否则会抛出错误 django.core.exceptions.AppRegistryNotReady: Models aren't loaded yet. ''' im

[DJANGO] excel十几万行数据快速导入数据库研究

先贴原来的导入数据代码: 8 import os os.environ.setdefault("DJANGO_SETTINGS_MODULE", "www.settings") ''' Django 版本大于等于1.7的时候,需要加上下面两句 import django django.setup() 否则会抛出错误 django.core.exceptions.AppRegistryNotReady: Models aren't loaded yet. ''' im

华为上机测试题(Excel表格纵列字母数字转换-java)

PS:这是我刚做的一道题,题目不难,满分60,得分40,大家看看哪里有问题,欢迎提意见,感谢! /* * 题目:Excel表格纵列字母数字转换 * 描述: 在Excel中列的编号为A-Z,AA-AZ,BA-BZ.....CZB.....,请实现一个函数要求满足以下功能,将编号进行修改, * 如A-Z为1-26,然后翻转为两位,AA为27,AB为28.....ZZ为702,然后翻转为3位,AAA=703,AAB=704... 输入的字符串最长只有4. 题目类别: 字符串 难度: 初级 分数: 60

10.4 Excel方式二维变色提示的表格

在10.3节中,整行变色提求鼠标指针经过的效果已经完成了,接下来继续改进它.实现类似于Excel的行列的二维提示,效果如图1所示,当鼠标指针经过某一个单元格时.相应的列头和行头单元格会同时变色. 实例文件位于网页学习网CSS教程资源的“第10章\02\pretty-3.htm”. 图1 表格的行列二维变色提示 注意:本案例需要不少JavaScript编程的配合,如果读者缺乏相应基础,学起来可能会有一点困难. 一.改造CSS代码 首先改造CSS设置,这个效果单纯使用CSS是无法实现的,必须要使用j

csv文件或者excel表格导入数据库

 将csv文件或者excel表格导入数据库的方法: Excel数据直接导入mysql会需要用到phpexcel开源类,详情使用可以参考这篇文章~ http://www.cnblogs.com/freespider/p/3284828.html 本文使用的方法是: Excel ——> CSV——>MySql 首先将excel另存为csv文件,然后开始分析数据. 代码如下: 1 <span style="font-size:18px;"><?PHP 2 //将

php语言中Excel表格导入数据库的方法详解

在php编程语言中,对于如何在Excel表格中导入数据库的方法是很多编程者比较头疼的一个问题,有些技术人员可能在百度尝试过搜索很多不同的问题,但是给出的答案经过自己测试之后,发现还是行不通,那么对此,燚轩科技也尝试了一下如何在Excel表格中导入数据库,现在将源代码展示给各位技术编程者,大家可以借鉴参考一下. public function saveexcel(){require_once('./Thinkphp/Extend/Vendor/PHPExcel-1.8/Classes/PHPExc

Excel应该这么玩——3、命名表格:彻底改造公式

上一篇介绍了通过命名列将公式中的地址引用去掉,让公式更容易理解.但是之前的命名列只是针对单个表格的,如何引用其他表格的列是本篇的主要内容. 1.创建命名表格 命名表格的前提的创建表格,这个操作上一篇已经介绍过了,选中数据区中的一个单元格,按Ctrl+T即可.本篇以产品销售为例,先创建产品表,如下: 然后定位到菜单的公式->名称管理器: 在弹出的名称管理器对话框中选中刚创建的表格对应的项,点击上方的编辑按钮: 修改表格名称: 编辑名称对话框中可以看到表格的引用位置是从A2到C5的区域.如果插入新的

从SSMS中复制代码到Word中数字消失--没解决&amp;&amp;Excel连接SQL Server数据库

1.因工作需要需把SSMS中的代码复制到word中,可发现一个问题: 从SQL Server2008的SSMS中复制代码到Word 2013中,如果是中文汉字+阿拉伯数字,阿拉伯数字会消失.如果是英文+阿拉伯数字就没有问题.在网上也没找到方法,问一哥们,他说我们都是英文,没遇到过.记录下来吧 2.每次发的数据都在数据库中,之前都是select * from TableName,然后"连同标题一起复制",然后再粘贴到Excel中.但其实excel可以连接SQL Server的,其实操作很