在 Birt 中實現交叉表的動態分組

來源:數據庫

  https://forums.opentext.com/forums/discussion/173783/dynamic-grouping-of-crosstab-in-birt#latestide

 

  在業務填報中,有時會須要基於時間段進行動態交叉分組統計,根據時間段長短實現按天、按周、按月、按年動態分組。例如:某企業根據業務須要,需按照2個參數(開始日期、結束日期)實現一段時間內訂單的統計。統計規則以下:工具

  示例:根據輸入的參數值,計算日期之間的差別。spa

  var diff = 結束日期-開始日期                ---- 相隔的天數
  若是(diff <15)
    將「日期組」分組以顯示爲日期
  若是(diff>15)
    將「日期組」分組以顯示爲周
  若是(diff >30)
    將「日期組」分組以顯示爲月份
  若是(diff>365)
    將「日期組」分組以顯示爲年份設計

 

  小夥伴們是否是有點不知所措了呢?上述問題實質上就是一個數據準備的問題,但是SQL或scripted data sources的方式代碼難寫,工做量大;退而求次使用報表隱藏列的方式,既不通用又很是彆扭。那麼,一個更好的解決方案就是在報表工具中引入集算器,解決諸類問題將垂手可得。下面咱們就以Birt報表工具爲例,介紹一下實現過程。對於其餘的報表工具,也是大同小異。blog

 

  在本例中,要根據參數輸入,統計企業從2012-07-04開始到2014-05-06結束這個時間段內的訂單總數,運貨費總數,訂單金額總數。數據表「ORDERS」中的原始數據以下:ip

  undefined

 

  咱們直接來看集算器解決這個問題的SPL代碼:get


A B C
1 =connect("demo") //鏈接數據庫
2 =A1.query("select   ORDERID,ORDERDATE,FREIGHT,ORDERAMOUNT from ORDERS where ORDERDATE >=? and   ORDERDATE <=?",startDate,endDate) //從 ORDERS 表中查詢出統計開始日期到結束日期之間的訂單數據,startDate 和 endDate 是日期參數。
3 =interval(startDate,endDate) //計算開始日期和結束日期的間隔天數
4 if A3>365 //若是天數間隔大於 365 天,則按年份分組
5
=startDate|A3.(elapse@y(startDate,~)) //計算出按年份的分組序表
6
=A2.group(B5.pseg(ORDERDATE);~.count(ORDERID):TotalOrder,round(~.sum(FREIGHT),2):TotalFreight,round(~.sum(ORDERAMOUNT),2):TotalOrderAmount,B5(#):BeginDate) //按 B5 區間對 A2 分組,統計出訂單總數,運貨費總數,訂單金額總數,保留兩位小數,並將 B5 做爲最後一列。
7
=B6.new(BeginDate:BeginDate,#2:TotalOrder,#3:TotalFreight,#4:TotalOrderAmount) //取出須要的數據列,生成新的結果序表
8
>A1.close() //關閉數據庫
9
return B7 //返回按年份分組的結果集
10 else if A3>30 //若是天數間隔大於 30 天 & 小於等於 365 天,則按月份分組
11
=startDate|A3.(elapse@m(startDate,~)) //計算出按月份的分組序表
12
=A2.group(B11.pseg(ORDERDATE);~.count(ORDERID):TotalOrder,round(~.sum(FREIGHT),2):TotalFreight,round(~.sum(ORDERAMOUNT),2):TotalOrderAmount,B11(#):BeginDate) //按 B11 區間對 A2 分組,統計出訂單總數,運貨費總數,訂單金額總數,保留兩位小數,並將 B11 做爲最後一列。
13
=B12.new(BeginDate:BeginDate,#2:TotalOrder,#3:TotalFreight,#4:TotalOrderAmount)
14
>A1.close()
15
return B13 //返回按月份分組的結果集
16 else if A3>15 //若是天數間隔大於 15 天 & 小於等於 30 天,則按星期分組
17
=startDate|A3.(elapse(startDate,7*~)) //計算出按星期的分組序表
18
=A2.group(B17.pseg(ORDERDATE);~.count(ORDERID):TotalOrder,round(~.sum(FREIGHT),2):TotalFreight,round(~.sum(ORDERAMOUNT),2):TotalOrderAmount,B17(#):BeginDate) /按 B17 區間對 A2 分組,統計出訂單總數,運貨費總數,訂單金額總數,保留兩位小數,並將 B17 做爲最後一列。
19
=B18.new(BeginDate:BeginDate,#2:TotalOrder,#3:TotalFreight,#4:TotalOrderAmount)
20
>A1.close()
21
return B19 //返回按星期分組的結果集
22 else //若是天數間隔小於 15 天,則按日期分組
23
=startDate|A3.(elapse(startDate,~)) //計算出按日期的分組序表
24
=A2.group(B23.pseg(ORDERDATE);~.count(ORDERID):TotalOrder,round(~.sum(FREIGHT),2):TotalFreight,round(~.sum(ORDERAMOUNT),2):TotalOrderAmount,B23(#):BeginDate) /按 B23 區間對 A2 分組,統計出訂單總數,運貨費總數,訂單金額總數,保留兩位小數,並將 B23 做爲最後一列。
25
=B24.new(BeginDate:BeginDate,#2:TotalOrder,#3:TotalFreight,#4:TotalOrderAmount)
26
>A1.close()
27
return B25 //返回按日期分組的結果集

 

  將集算器SPL代碼存爲order.dfx文件,而後引入到Birt報表中。如何引用請參看乾學院文章《BIRT調用SPL腳本》。it

 

  在BIRT報表中設計表以下:io

  undefined

 

  報表調用集算器的方法和調用存儲過程徹底同樣,好比在 BIRT 的存儲過程數據集中能夠用 call orders(?,?) 來調用。

  接下來,咱們看一下WEB預覽時,輸入不一樣參數的預覽結果:

  (1)輸入參數:開始時間 2012-07-04,結束時間 2014-05-06    間隔天數大於365,按照年份分組顯示。

  undefined

  undefined

 

  (2)輸入參數:開始時間 2012-07-15,結束時間 2012-12-03    間隔天數大於30,按照月份分組顯示。

  undefined

  undefined

 

  (3)輸入參數:開始時間 2012-07-20,結束時間 2012-08-15    間隔天數大於15,按照星期分組顯示。

  undefined

  undefined

 

  (4)輸入參數:開始時間 2012-07-04,結束時間 2012-07-18    間隔天數小於15,按照日期分組顯示。

  undefined

  undefined

相關文章
相關標籤/搜索