.Net core NPOI导出Excel(csv)优化

时间:2020-03-26
本文章向大家介绍.Net core NPOI导出Excel(csv)优化,主要包括.Net core NPOI导出Excel(csv)优化使用实例、应用技巧、基本知识点总结和需要注意事项,具有一定的参考价值,需要的朋友可以参考一下。

    记得第一篇文章就是.net core 通过NPOI 导入导出excel(csv),之前的那种方式由于我们需要自定表头,每次都要手动写表头非常麻烦。特别是非常多列表头的时候我们得崩溃,,不利于扩展。

所以之后就想着有没有试着获取属性的描述来设置表头,果然尝试成功,然后就方便多了。

首先我们来看之前的导出代码:

        public static byte[] OutputExcel(List<T> entitys, string[] title)
        {
            IWorkbook workbook = new XSSFWorkbook();
            ISheet sheet = workbook.CreateSheet("sheet");
            IRow Title = null;
            IRow rows = null;
            Type entityType = entitys[0].GetType();
            PropertyInfo[] entityProperties = entityType.GetProperties();

            for (int i = 0; i <= entitys.Count; i++)
            {
                if (i == 0)
                {
                    Title = sheet.CreateRow(0);
                    for (int k = 1; k < title.Length + 1; k++)
                    {
                        Title.CreateCell(0).SetCellValue("序号");
                        Title.CreateCell(k).SetCellValue(title[k - 1]);
                    }

                    continue;
                }
                else
                {
                    rows = sheet.CreateRow(i);
                    object entity = entitys[i - 1];
                    for (int j = 1; j <= entityProperties.Length; j++)
                    {
                        object[] entityValues = new object[entityProperties.Length];
                        entityValues[j - 1] = entityProperties[j - 1].GetValue(entity);
                        rows.CreateCell(0).SetCellValue(i);
                        rows.CreateCell(j).SetCellValue(entityValues[j - 1].ToString());
                    }
                }
            }

            byte[] buffer = new byte[1024 * 2];
            using (MemoryStream ms = new MemoryStream())
            {
                workbook.Write(ms);
                buffer = ms.ToArray();
                ms.Close();
            }

            return buffer;
        }

这个函数需要两个参数,一个是要导出的list,一个是表头,假设我们表头有三十个,那我们写表头都崩溃了。

但是我们的实体的属性是一定会写的,所以这个时候就需要我们改造一下了:

首先我们先去获取实体属性的description描述,相信这个在我们建立实体属性的时候就已经写好了,就不用写第二次了。

        /// <summary>
        /// 获取描述
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="obj"></param>
        /// <returns></returns>
        private static string GetEnumDescription(PropertyInfo obj)
        {
            DescriptionAttribute descAttr = Attribute.GetCustomAttribute(obj, typeof(DescriptionAttribute)) as DescriptionAttribute;
            if (descAttr == null)
            {
                return string.Empty;
            }

            return descAttr.Description;
        }

可以看到我们将属性信息传入进去就可以获取了,只要不是导出超大的excel这里使用的反射可以忽略不计,

然后看看改造之后的代码:

        /// <summary>
        /// 导出不需要表头
        /// </summary>
        /// <param name="entitys"></param>
        /// <param name="title"></param>
        /// <returns></returns>
        public static byte[] OutputFileOutofTitle(List<T> entitys)
        {
            IWorkbook workbook = new XSSFWorkbook();
            ISheet sheet = workbook.CreateSheet("sheet");
            IRow Title = null;
            IRow rows = null;

            if (entitys.Count == 0)
            {
                Type entityType = entitys[0].GetType();
                PropertyInfo[] entityProperties = entityType.GetProperties();
                Title = sheet.CreateRow(0);
                for (int k = 1; k < entityProperties.Length + 1; k++)
                {
                    Title.CreateCell(0).SetCellValue("序号");
                    Title.CreateCell(k).SetCellValue(GetEnumDescription(entityProperties[k - 1]));
                }
            }
            else
            {

                Type entityType = entitys[0].GetType();
                PropertyInfo[] entityProperties = entityType.GetProperties();

                for (int i = 0; i <= entitys.Count; i++)
                {
                    if (i == 0)
                    {
                        Title = sheet.CreateRow(0);
                        for (int k = 1; k < entityProperties.Length + 1; k++)
                        {
                            Title.CreateCell(0).SetCellValue("序号");
                            Title.CreateCell(k).SetCellValue(GetEnumDescription(entityProperties[k - 1]));
                        }

                        continue;
                    }
                    else
                    {
                        rows = sheet.CreateRow(i);
                        object entity = entitys[i - 1];
                        for (int j = 1; j <= entityProperties.Length; j++)
                        {
                            object[] entityValues = new object[entityProperties.Length];
                            entityValues[j - 1] = entityProperties[j - 1].GetValue(entity);
                            rows.CreateCell(0).SetCellValue(i);
                            if (entityValues[j - 1] != null)
                            {
                                rows.CreateCell(j).SetCellValue(entityValues[j - 1].ToString());
                            }
                        }
                    }
                }
            }

            byte[] buffer = new byte[1024 * 2];
            using (MemoryStream ms = new MemoryStream())
            {
                workbook.Write(ms);
                buffer = ms.ToArray();
                ms.Close();
            }

            return buffer;
        }

这里直接通过类型获取属性信息,之后再获取属性中的描述,其实挺简单的,记录一下吧,要不然又忘了。

原文地址:https://www.cnblogs.com/Ivan-Wu/p/12573056.html