zoukankan      html  css  js  c++  java
  • JXLS (Excel导入、导出工具使用)

    JXLS (Excel导入、导出工具使用)

    1:简介:

           jxls是一个简单的、轻量级的excel导出库,使用特定的标记在excel模板文件中来定义输出格式和布局。java中成熟的excel导出工具有pol、jxl,但他们都是使用java代码的方式来导出excel,编码效率很低且不方便维护。

    还可以使用一些工具很轻松的实现模板导出。这些工具现在还在维护,而且做得比较好的国内的有easyPOI,国外的就是这个JXLS了。

    比较:

    项目中有很多复杂的报表(大量单元格合并和单元格样式),easyPOI处理合并单元格时候容易出现残损的情况,poi代码维护成本高。

    2:maven依赖:

    <dependency>
    <groupId>org.jxls</groupId>
    <artifactId>jxls</artifactId>
    <version>[2.6.0-SNAPSHOT,)</version>
    </dependency>
    <dependency>
    <groupId>org.jxls</groupId>
    <artifactId>jxls-poi</artifactId>
    <version>[1.2.0-SNAPSHOT,)</version>
    </dependency>
    <dependency>
    <groupId>org.jxls</groupId>
    <artifactId>jxls-jexcel</artifactId>
    <version>[1.0.8,)</version>
    </dependency>
    <dependency>
    <groupId>org.jxls</groupId>
    <artifactId>jxls-reader</artifactId>
    <version>[2.0.5,)</version>
    </dependency>

    2:下面先做一个简单导出的实现:

    1: 创建model:

     2:先用office创建一个xlsx的模板

     

    可以看到这里有一些cell 的文本批注,office中添加批注快捷键(Shit + F2),批注中的类容这里先不做解释,下面会讲到

    3:工具类JxlsUtils.java

    public class JxlsUtils{
         
        private static final String TEMPLATE_PATH="jxls-template";
         
        public static void exportExcel(InputStream is, OutputStream os, Map<String, Object> model) throws IOException{
            Context context = new Context();
            if (model != null) {
                for (String key : model.keySet()) {
                    context.putVar(key, model.get(key));
                }
            }
            JxlsHelper jxlsHelper = JxlsHelper.getInstance();
            Transformer transformer  = jxlsHelper.createTransformer(is, os);
            JexlExpressionEvaluator evaluator = (JexlExpressionEvaluator)transformer.getTransformationConfig().getExpressionEvaluator();
            Map<String, Object> funcs = new HashMap<String, Object>();
          //  funcs.put("utils", new JxlsUtils());    //添加自定义功能
          //  evaluator.getJexlEngine().setFunctions(funcs);
            jxlsHelper.processTemplate(context, transformer);
        }
     
        public static void exportExcel(File xls, File out, Map<String, Object> model) throws FileNotFoundException, IOException {
                exportExcel(new FileInputStream(xls), new FileOutputStream(out), model);
        }
         
        public static void exportExcel(String templateName, OutputStream os, Map<String, Object> model) throws FileNotFoundException, IOException {
            File template = getTemplate(templateName);
            if(template!=null){
                exportExcel(new FileInputStream(template), os, model);    
            }
        }
         
         
        //获取jxls模版文件
     
        public static File getTemplate(String name){
            String templatePath = JxlsUtils.class.getClassLoader().getResource(TEMPLATE_PATH).getPath();
            File template = new File(templatePath, name);
            if(template.exists()){
                return template;
            }
            return null;
        }    
         
        // 日期格式化
        public String dateFmt(Date date, String fmt) {
            if (date == null) {
                return "";
            }
            try {
                SimpleDateFormat dateFmt = new SimpleDateFormat(fmt);
                return dateFmt.format(date);
            } catch (Exception e) {
                e.printStackTrace();
            }
            return "";
        }
         
        // if判断
        public Object ifelse(boolean b, Object o1, Object o2) {
            return b ? o1 : o2;
        }
         
    }

    上面注释中的自定义功能可以先注释到,我们后面在讲

    入口ObjectCollectionDemo.java

    public class ObjectCollectionDemo {
        static Logger logger = LoggerFactory.getLogger(ObjectCollectionDemo.class);
         
        public static void main(String[] args) throws ParseException, IOException {
            logger.info("Running Object Collection demo");
             
            List<Employee> employees = generateSampleEmployeeData();
            OutputStream os = new FileOutputStream("target/object_collection_output.xls");
            Map<String , Object> model=new HashMap<String , Object>();
            model.put("employees", employees);
            model.put("nowdate", new Date());
            JxlsUtils.exportExcel("object_collection_template.xls", os, model);
            os.close();
        }
     
        public static List<Employee> generateSampleEmployeeData() throws ParseException {
            List<Employee> employees = new ArrayList<Employee>();
            SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MMM-dd", Locale.US);
            employees.add( new Employee("Elsa", dateFormat.parse("1970-Jul-10"), 1500, 0.15) );
            employees.add( new Employee("Oleg", dateFormat.parse("1973-Apr-30"), 2300, 0.25) );
            employees.add( new Employee("Neil", dateFormat.parse("1975-Oct-05"), 2500, 0.00) );
            employees.add( new Employee("Maria", dateFormat.parse("1978-Jan-07"), 1700, 0.15) );
            employees.add( new Employee("John", dateFormat.parse("1969-May-30"), 2800, 0.20) );
            return employees;
        }
    }

    生成效果:

     好的,这样就很轻松的导出了是不是很简单


    3:下面讲一下导出的细节,注意事项:

    1:模板中的批注:

    注意如果模板中对单元格加了批注,但是没有批注信息的话可能会报错:

     1-1:bean属性标记

    jxls使用 Apache JEXL表达式语言来解析定义在excel模板中的表达式。JEXL与JSTL相似,并对JSTL进行了扩展。eg:

    ${department.chief.age} //属性可以是无限深度

    ${utils:dateFmt(date,"yyyy-MM-dd")} //自定义工具函数

    1-2:XLS Area定义标记

    XLS Area 是JxlsPlus中的一个重要概念,它代表excel模板中需要被解析的矩形区域,由A1到最后一个单元格表示,有利于加快解析速度。

    XLS Area 使用excel注释标注表示,它需要被定义在excel 模板的第一个单元格(A1):

    jx:area(lastCell = "<AREA_LAST_CELL>")

    1-3:XLS Command表示标记

    XLS Command 使用excel注释标注表示,命令格式如下:

    jx:<command_name>(attr1='val1' attr2='val2' ... attrN='valN' lastCell=<last_cell> areas=["<command_area1>", "<command_area2", 
    ... "<command_areaN>"])

    <command_name> 是库自带的命名或是用户自定义并注册到XlsCommentAreaBuilder的命令。

    each 命令是最常用的XLS命令,形如:

    jx:each(items="employees" var="employee" lastCell="D4")

    eg:

    each 可以有如下一些属性:

    • items 上下文中集合的变量名;
    • var 在遍历集合的时候每一条记录的变量名;
    • area 该XLS Command的解析区域;
    • direction 数据在excel中填充的方向,默认(DOWN)向下;
    • select 其值为一个表达式,用来过滤数据

     横向遍历显示list的数据:

     jx:each(items="data" var="dat" lastCell="A3" direction="RIGHT")

     1-4:jexl自定义工具函数:

    如果你需要自定jexl来处理数据,你可以从Transformer对象获取JexlEngine引用,并对其配置。

    下面的例子实现了将一个自定义jexl函数注册到utils命名空间下:

    JxlsHelper jxlsHelper = JxlsHelper.getInstance();
    Transformer transformer = jxlsHelper.createTransformer(is, os);
    JexlExpressionEvaluator evaluator = (JexlExpressionEvaluator)transformer.getTransformationConfig().getExpressionEvaluator();
    Map<String, Object> funcs = new HashMap<String, Object>();
    funcs.put("utils", new JxlsUtils()); //添加自定义功能
    evaluator.getJexlEngine().setFunctions(funcs);

     1-5:单元格合并命令:

    Excel注释语法

    jx:merge(
    lastCell =“合并单元格范围” 
    [,cols =“合并的列数”] 
    [,rows =“合并的行数”] 
    [,minCols =“要合并的最小列数”] 
    [,minRows = “要合并的最小行数”] 
    )

    注意:此命令只能用于尚未合并的单元格。如果合并单元格的合并单元格范围存在,则会发生异常。

    官方文档:http://jxls.sourceforge.net/reference/excel_markup.html

    官方文档打不开?下个加速器就可以了:http://www.youxia66.com/

    参考博客:https://www.cnblogs.com/klguang/p/6425422.html

    博客源码:

    demo工程源码下载http://files.cnblogs.com/files/klguang/jxlsdemo.zip

  • 相关阅读:
    课堂作业04 2017.10.27
    课程作业 03 动手动脑 2017.10.20
    课程作业 03 2017.10.20
    HDU 3974 Assign the task
    POJ 2155 Matrix
    POJ 2481 Cows
    HDU 3038 How Many Answers Are Wrong
    CS Academy Array Removal
    POJ_1330 Nearest Common Ancestors LCA
    CF Round 427 D. Palindromic characteristics
  • 原文地址:https://www.cnblogs.com/dw3306/p/11098841.html
Copyright © 2011-2022 走看看