Map-Reduce 思想在 ABAP 编程中的一个实际应用案例
ABAP 是一門企業級應用編程語言,其 740 版本于 2013 年發布,增添了許多新的語法和關鍵字:
其中一個亮點就是新引入的 REDUCE 關鍵字。這個關鍵字的作用和在大規模數據集并行計算領域里廣泛使用的 Map-Reduce 編程模型中的 Reduce 操作類似,可以按照字面意思理解為歸約 。
什么是 Map-Reduce 思想?
Map-Reduce 是一種編程模型和相關實現,用于在集群上使用并行分布式算法,生成和處理大規模數據集。
一個 Map-Reduce 程序由一個 Map 過程和一個 Reduce 方法組成。Map 過程負責執行過濾和排序,例如將學生按名字排序到隊列中,每個名稱由一個隊列維護。
Reduce 方法負責執行匯總操作,例如計算學生的數量。
Map-Reduce 系統通過編排分布式服務器,來并行運行各種任務,管理系統各個部分之間的所有通信和數據傳輸,以及提供數據冗余,實現容錯機制。
下圖是 Map Reduce 框架的工作步驟,統計一個海量輸入數據集(比如大于 1TB )中的單詞出現次數。工作步驟包含 Splitting, Mapping, Shuffling, Reducing 以得到最后的輸出結果。
Map-Reduce 編程模型已經廣泛運用于大數據處理領域的工具和框架,比如 Hadoop 之中。
Map-Reduce 在 CRM 系統中的一個實際應用
我們來看一個筆者工作中的實際任務。我需要在某個 CRM 測試系統上做個統計,列出在數據庫表 CRM_JSTO 里,OBTYP(Object Type) 和 STSMA(Status Schema) 這兩列擁有相同值的內表行的個數。大家可以把 OBTYP 和 STSMA 兩列具有相同值的內表行 這個描述,類比成上圖中重復出現的單詞。
下圖是系統中數據庫表 CRM_JSTO 的部分行:
下圖是筆者最終完成的統計結果:
測試系統上數據庫表總的行數超過 55 萬行,其中有 90279 行,只維護了 OBTYP 為TGP,而沒有維護 STSMA.
排名第二的是 COH 和 CRMLEAD 的組合,出現了 78722 次。
上圖這個結果是怎么統計出來的呢?
稍稍做過一些 ABAP 開發的朋友們,一定會立即寫出下面的代碼:
利用 SELECT COUNT 直接在數據庫層完成統計工作。這也是 SAP 推薦的做法,即所謂 Code pusudown 準則,即能放到 HANA 數據庫層面進行的操作,就盡量放進去,以充分利用 HANA 強大的計算能力。在數據庫能夠完成計算邏輯的前提下,盡量避免把計算邏輯放到 Netweaver ABAP 應用層去做。
不過,我們也需要注意到這種方式的局限性。SAP CTO 曾經有過一句名言:
There is no future with ABAP alone
There is no future in SAP without ABAP
未來的 ABAP 會走向開放,互聯的道路。回到這個需求本身,假設待檢索的輸入數據不是從 ABAP 數據庫表中來,而是來自 HTTP 請求,或者第三方系統發過來的 IDOC,此時我們無法再使用 OPEN SQL 本身的 SELECT COUNT 操作,而只能在 ABAP 應用層解決這個問題。
下面介紹兩種用 ABAP 編程語言完成這一需求的解決方案。
第一種方式比較傳統,實現在方法 get_result_traditional_way 里:
ABAP 的 LOOP AT GROUP BY 這個關鍵字組合簡直就像是為這個需求量身定做一般:給 GROUP BY 指定 obtyp 和 stsma 這兩列,然后 LOOP AT 會自動將輸入內表的行記錄根據這兩列的值進行分組,每組行記錄的個數通過關鍵字 GROUP SIZE 自動計算出來,每組各自的 obtyp 和 stsma 的值,以及組內行記錄的條目數,存儲在 REFERENCE INTO 指定的變量 group_ref 里。ABAP 開發人員需要做的事情,只是簡單地把這些結果存儲到輸出內表即可。
第二種辦法,就是本文標題所述,使用 ABAP 740 新引入的 REDUCE 關鍵字:
REPORT zreduce1.DATA: lt_status TYPE TABLE OF crm_jsto.SELECT * INTO TABLE lt_status FROM crm_jsto.DATA(lo_tool) = NEW zcl_status_calc_tool( ).lo_tool = REDUCE #( INIT o = lo_toollocal_item = VALUE zcl_status_calc_tool=>ty_status_result( )FOR GROUPS <group_key> OF <wa> IN lt_statusGROUP BY ( obtyp = <wa>-obtyp stsma = <wa>-stsma )ASCENDING NEXT local_item = VALUE #( obtyp = <group_key>-obtypstsma = <group_key>-stsmacount = REDUCE i( INIT sum = 0 FOR m IN GROUP <group_key>NEXT sum = sum + 1 ) )o = o->add_result( local_item ) ).DATA(ls_result) = lo_tool->get_result( ).上面的代碼乍一看可能覺得有點晦澀,但仔細閱讀后發現這種方式本質上也采用了和方法一 LOOP AT GROUP BY 同樣的分組策略——根據 obtyp 和 stsma 分組,這些子組通過變量 group_key標識,然后通過第 10 行的 REDUCE 關鍵字,通過累加的方式,手動計算這個組的條目數——把一個大的輸入集根據 GROUP BY 指定的條件歸約成一個個規模更小的子集,然后分別針對子集進行計算——這就是 REDUCE 關鍵字通過字面含義傳遞給 ABAP 開發人員的處理思想。
總結和比較一下這三種實現方式:當待統計的數據源為 ABAP 數據庫表時,一定優先選用 OPEN SQL 的方式,使計算邏輯在數據庫層完成,以獲得最佳的性能。
當數據源并非 ABAP 數據庫表,而分組統計的需求為簡單的計數操作(COUNT)時, 優先用LOOP AT … GROUP BY … GROUP SIZE,使得計數操作通過 GROUP SIZE 在ABAP kernel 完成,以獲得較好的性能。
當數據源并非 ABAP 數據庫表,而分組統計的需求為自定義的邏輯時,用本文介紹的第三種 REDUCE 解法,將自定義統計邏輯寫在第 11 行的 NEXT 關鍵字后。
三種解法的性能評測
我編寫了一個簡單的報表進行性能評測:
DATA: lt_status TYPE zcl_status_calc_tool=>tt_raw_input.SELECT * INTO TABLE lt_status FROM crm_jsto.DATA(lo_tool) = NEW zcl_status_calc_tool( ).zcl_abap_benchmark_tool=>start_timer( ). DATA(lt_result1) = lo_tool->get_result_traditional_way( lt_status ). zcl_abap_benchmark_tool=>stop_timer( ).zcl_abap_benchmark_tool=>start_timer( ). lo_tool = REDUCE #( INIT o = lo_toollocal_item = VALUE zcl_status_calc_tool=>ty_status_result( )FOR GROUPS <group_key> OF <wa> IN lt_statusGROUP BY ( obtyp = <wa>-obtyp stsma = <wa>-stsma )ASCENDING NEXT local_item = VALUE #( obtyp = <group_key>-obtypstsma = <group_key>-stsmacount = REDUCE i( INIT sum = 0 FOR m IN GROUP <group_key>NEXT sum = sum + 1 ) )o = o->add_result( local_item ) ).DATA(lt_result2) = lo_tool->get_result( ). zcl_abap_benchmark_tool=>stop_timer( ).ASSERT lt_result1 = lt_result2.測試數據如下:
這三種解法的性能依次遞減,不過適用的場合和靈活程度依次遞增。
LOOP AT ... GROUP BY ... GROUP SIZE 這種解決方案,在筆者工作的 ABAP 測試服務器上,處理 55 萬條記錄,用了 0.3 秒,而 REDUCE 則需花費 0.8 秒, 兩種解法的性能處于同一數量級之內。
總結
Map-Reduce 是一種編程模型和相關實現,用于在集群上使用并行分布式算法,生成和處理大規模數據集。ABAP 編程語言從語言層面支持對大規模數據的 REDUCE 操作。本文分享了筆者工作中使用 Map-Reduce 思路處理大規模數據集的一個實際案例,并與傳統的另外兩種解決方案做了比較。在性能不遜于傳統解決方案的前提下,基于 Map-Reduce 的解決方案,具有更為廣泛的應用場合和可擴展性。希望本文分享的內容對大家使用 ABAP 處理類似問題時有所啟發,感謝閱讀。
總結
以上是生活随笔為你收集整理的Map-Reduce 思想在 ABAP 编程中的一个实际应用案例的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 《塞尔达传说:荒野之息》CEMU模拟器操
- 下一篇: 魔兽世界冥殇裂片怎么获得