有时报表在展现或导出时需要从数据库中取出较多数据,而JDBC的取数速度一向比较慢,有可能超过报表其它运算环节的耗时,导致整个报表的生成过程效率极低。下面我们看如何利用润乾集算报表的并行计算机制提高JDBC的取数性能。

    所谓并行取数是指,使用多线程技术在报表工具与数据库建立多个连接,同时读取一份源数据,这需要将源数据分段,每个线程(数据库连接)读取其中一段内容,最后将所有线程的结果合并得到总目标数据的过程。

    集算报表内置了并行机制可以很容易完成并行取数任务,从而提升报表性能,这里以oracle为例说明实现过程。

报表描述

    用户状态表展现的是明细数据,由于需要导出,必须一次性读取数据表中所有数据。单表数据量为360万,报表样式为:

wKioL1SiVETxLPr0AAA5fJBk9Oo863.jpg

编写脚本

使用集算器编写脚本(parallel.dfx),实现并行取数逻辑。首先确定分段字段,这里选择数值型的userid字段,再据设定的线程数和userid最大值(指定为大数值常量)计算每段中userid的范围;最后根据指定的数据范围通过sql分段读取数据,完成多线程取数过程。以下为实现脚本:

wKiom1SiU5ChxFXRAAGPz-ZUALQ335.jpg

 A5fork使用多线程执行网格中的代码块,实现并行取数;

 B6-B9完成并行取数,每个线程运行结果返回A8格;

 A10为报表返回合并后的结果集。

编制报表

    新建报表模板后,数据集选择集算器,在数据集编辑窗口指定上述编辑好的dfx文件,完成数据集创建。

    设置报表模板表达式:

wKioL1SiVETj0bABAABtOdvOsKg398.jpg

    A2:根据数据集ds1使用select函数取用户登录信息列表;

    A2-G2:根据A2扩展,通过取值表达式分别取用户ID、账户、在线等信息。

并行后效果

    报表运行后记录数据集计算时间,分别比较并行前和并行后的运行结果:

wKiom1SiU5CjB6jgAABJ1JILVGU722.jpg

    上面看到了并行取数带来的效果,通过集算报表的并行机制可以加速取数过程,从而提升了整体报表性能,测试结果因测试环境而异,本机配置详见附录。

使用多线程并行取数适合数据库资源比较空闲(如连接数未达上线)的情况,通过这种方式充分利用数据库资源。如果数据库任务已经饱和,这种方法会进一步加重数据库负担,而不会起到提高速度的作用。

此外,分段字段的选择对性能影响较大。最好是选择递增插入的有索引字段,如作为主键的流水号,这样数据库能充分利用索引减少遍历范围;尽量选择数值类型的字段,作为条件的运算性能更高且易于拆分。实际操作中要综合考虑这两方面因素,本例中由于没有索引和主键,所以选择了数值型userid。实际业务中经常能找到递增插入的有索引数值型字段,采用并行取数的方式获得的性能提升也会更好。

【附】测试机配置

测试机型Dell Inspiron 3420

CPUIntel Core i5-3210M @2.50GHz *4

RAM4G

HDD:西数WDC(500G 5400/)

操作系统Win7(X64) SP1

JDK1.6

数据库:oracle11g R2

集算报表版本5.0