当前位置: 首页 > 后端技术 > Java

使用开源计算引擎提高Excel格式文件的处理效率

时间:2023-04-01 17:16:51 Java

解析、生成、查询、计算Excel是Java下比较常见的工作,但是Excel的文件格式很复杂,难度太大自己编码和阅读。POI\EasyExcel\JExcel等类库就方便多了,其中POI最好。POI具有全面详细的xls读写能力。POI可以读写多种Excel文件格式。它同时支持古老的二进制格式(xls)和现代的OOXML格式(xlsx)。既支持全内存一次性读写,也支持小内存流式读写。POI为大量Excel元素设计了相应的JAVA类,包括工作簿、打印机、工作表、行、单元格。与单元格相关的类包括单元格样式、字体、颜色、日期、对齐方式、边框等,仅单元格样式类就有四十多个方法,可以进行最全面、最细致的读写操作。POI的读写功能非常底层。POI的读写功能全面细致,但细致也意味着太低级。开发人员必须从头开始编写并自己处理每个细节。即使是简单的操作也需要大量代码。比如,读入开始为列名的行式xls:FileInputStreamfileInputStream=newFileInputStream("d:\\Orders.xls");//gettheexcelbookWorkbookworkbook=newHSSFWorkbook(fileInputStream);if(workbook!=null){//获取第一个工作表Sheetsheet=workbook.getSheetAt(0);if(sheet!=null){//获取col名称/第一行RowrowTitle=sheet.getRow(0);//第一行if(rowTitle!=null){intcellTitles=rowTitle.getPhysicalNumberOfCells();//获取列号for(inti=0;isheet->line->cell的顺序进行循环分析,导致这样的繁琐的代码。这只是简单地读出数据。如果下一步要对数据进行处理,需要提前将其转化为结构化数据对象,比如ArrayList或者HashMap,代码就更繁琐了。POI查询计算难解析Excel不是目标,我们通常需要查询计算这些文件,但是POI作为Excel的分析类,没有也不适合提供相关方法,只能手工编写在Java中。比如基本的分组汇总操作,JAVA代码大致是这样的:(s2.salesman)){返回s1.salesman.compareTo(s2.salesman);}else{返回s1.ID.compareTo(s2.ID);}}};Collections.sort(sales,comparator);ArrayListresult=newArrayList();salesRecordstandard=sales.get(0);floatsumValue=standard.value;for(inti=1;i1000&&Amount<=3000&&like(Client,"S"))排序:A1.sort(Client,-Amount)"Deduplication:A1.id(Client)"关联两个xlsx:join(T("D:/Orders.xlsx"):O,SellerId;T("D:/Employees.xls"):E,EId).new(O.OrderID,O.Client,O.SellerId,O.Amount,O.OrderDate,E.Name,E.Gender,E.Dept)"TopN:T("D:/Orders.xls").top(-3;Amount)TopN(窗口函数)组内:T("D:/Orders.xls").groups(Client;top(3,Amount))SPL支持大量的日期函数和字符串函数,代码量更短,开发效率更高例如:时间函数,日期增减:elapse("2020-02-27",5)//return2020-03-03weekDay:day@w("2020-02-27")//返回5,即一周中第4N个工作日后的日期:workday(date("2022-01-01"),25)//返回2022-02-04String类函数,判断是否所有数字都是:isdigit("12345")//返回true得到子串前面的字符串:substr@l("abCDcdef","cd")//returnabCD按竖线Splitintoarrayofstrings:"aa|bb|cc".split("|")//return["aa","bb","cc"]SPL还支持年份增减、查找年份、查找季度、根据正则表达式拆分字符串、拆分where或选择部分SQL、拆分单词、按标签拆分HTML等。SPL提供了标准的SQL语法,可以像数据库表一样直接查询xls文件,大大降低了数据库程序员的学习门槛:filter:$select*fromd:/sOrder.xlsxwhereClientlike'%S%'or(Amount>1000andAmount<=2000)sort:$select*fromsales.xlsorderbyClient,Amontdescdistinct:$selectdistinct(sellerid)fromsales.xlsgroupby...having:$selectyear(orderdate)y,sum(amount)sfromsales.xlsgroupbyyear(orderdate)havingsum(amount)>=2000000join:$selecte.name,s.orderdate,s.amountfromsales.xlssleftjoinemployee.xlsxeons.sellerid=e.eidSPL支持SQL-92标准中的大部分语法,包括setcalculation,casewhen,with,nestedsubqueries等,见《没有 RDB 也敢揽 SQL 活的开源金刚钻 SPL》内容不规则的xls,一般类库无能为力,SPL语法是功能灵活丰富,轻松解决。比如Excel单元格中有很多“key=value”形式的字符串,需要整理成一个标准化的二维表进行后续计算:逻辑计算复杂,SQL和存储过程实现难度大,以及SPL具有更强的计算能力,可以轻松解决此类问题。比如计算某只股票的最长连续上涨天数:SPL支持更好的应用架构SPL是一种解释型语言,提供JDBC接口,可以通过JAVA以SQL或存储过程的形式集成,不仅减少了架构的耦合,也支持热插拔。SPL也支持多数据源,支持跨数据源计算。SPL提供了JDBC接口,可以方便的被JAVA调用。简单的SPL代码可以像SQL一样直接嵌入到JAVA中,比如条件查询:Class.forName("com.esproc.jdbc.InternalDriver");Connectionconnection=DriverManager.getConnection("jdbc:esproc:local://");Statementstatement=connection.createStatement();Stringstr="=T(\"D:/Orders.xls\").select(Amount>1000&&Amount<=3000&&like(Client,\"*S*\"))";ResultSetresult=statement.executeQuery(str);SPL支持外部计算,可以降低计算代码与前端应用的耦合度。复杂的SPL代码可以先保存为脚本文件,然后以存储过程的形式被JAVA调用:local://");CallableStatementstatement=conn.prepareCall("{callscriptFileName(?,?)}");statement.setObject(1,"2020-01-01");statement.setObject(2,"2020-01-31");statement.execute();SPL是解释型语言,可以通过外部代码实现热切换。解释型语言无需编译,修改后可立即执行,无需重启JAVA应用,减少维护工作量,提高系统稳定性。SPL支持多种文件数据源。除了xls,SPL还可以读写csv\txt\XML\Json等文件,比如txt的条件查询:T("sOrders.txt").groups(SellerId;sum(Amount))$select*fromd:/sOrders.txtwhereClientlike'%S%'or(Amount>1000andAmount<=2000)SPL支持跨数据源的计算,比如xls和txt的关联计算:=join(T("D:/Orders.xlsx"):O,SellerId;T("D:/Employees.txt"):E,EId).new(O.OrderID,O.Client,O.SellerId,O.Amount,O.OrderDate,E.Name,E.Gender,E.Dept)》SPL还可以访问各种关系型数据库,WebService,Restful等网络服务,Hadoop,redis,Kafka,Cassandra等NoSQL。POI只适合简单的xls解析/生成任务,不提供查询计算能力,SPL对POI进行封装,内置高级读写功能,不仅可以大大简化代码,还可以执行不规则甚至非常不规则的xls解析/生成任务,SPL额外提供强大的计算能力,不仅支持日常的Excel查询计算,还可以计算内容不规则、逻辑复杂的xls。SPL支持更好的应用架构,可以实现代码低耦合和热切换,支持多数据源和跨数据源计算。##SPL资料SPL官网SPL下载SPL源码欢迎添加对SPL感兴趣的小帮手(VX号:SPL-helper),进入SPL技术交流群,欢迎关注我的公告号:AntetokounmpoMiscellaneoustalk,回复003赠送作者专栏《docker修炼之道》的PDF版,30多篇docker优质文章。字母哥博客:zimug.com