鄭靈逸,李擎
(1.北京信息科技大學自動化學院,北京 100192;2.高動態導航技術北京市重點實驗室,北京 100192)
在如今的大數據時代[1],大數據的處理和查詢越來越成為研究的重點和技術攻克的難關,其中主要的問題在于數據量級龐大并且數據每日更新,一方面很難對如此大量的數據做到有效的管理,另一方面也很難從數據量為Pb[2]的數據中得到所需要的數據。MySql 作為一種最流行的關系型數據庫,它有著查詢效率高、數據準確且無數據重復的特點,在數據量為Gb的數據處理場景當中被廣泛使用。然而,在大數據處理場景之下[3],MySql存在明顯的缺點,MySql在使用大量存儲過程中每個連接的內存使用量將會大大增加,由于MySql 不允許調試存儲的特點,使得開發和維護存儲過程都較為困難。為了能夠更好存儲和處理Pb 級別的數據量,從大數據應用場景下提取所需要的數據,許多學者將Hadoop生態系統下的Hive數據庫作為大數據場景下的存儲和處理工具,并將SQL 作為Hive的查詢工具。Hadoop 是一個開發和運行處理大數據的軟件平臺,是Apache 的一個用Java 語言實現的開源軟件框架,實現通過大量計算機組成的集群對海量數據進行分布式計算。Hadoop 的核心是HDFS[4]、MapReduce 和YARN,這使得它具有可靠、高效、可伸縮的特點[5]。Hive是基于Hadoop的一個數據倉庫工具,用來進行數據提取、轉化、加載,是一種可以存儲、查詢和分析存儲在Hadoop 中的大規模數據的工具。Hive 數據庫由于其具有提供類SQL 查詢語言HQL[6]、為超大數據集設計了計算和擴展能力[7]以及提供統一的元數據管理等優點,是其他大數據處理技術無法比擬的。其工作原理是把編寫的SQL 語句進行解析,翻譯成MapReduce 代碼,然后在Hadoop 上執行[8]。因此,可以使用Hive 解決大數據場景下數據存儲、處理和查詢的問題。
一些學者發現在Hadoop平臺上用Hive處理大數據時,在數據量超過Pb并且SQL查詢語句冗長同時所需要的指標查詢過多[9]的情況下,仍然會出現數據處理查詢時間過長的問題。針對這一現象,馬鐵[10]提出了一種專為大規模數據處理而設計的快速通用的計算引擎Spark,不同于Hadoop MapReduce的是在Spark當中任務的中間輸出結果可以保存在內存當中[11],由于這一特性,Spark在大數據場景下表現出來具有更快更高效的特性。但是Spark 本身沒有自己的存儲與Meta 庫兩種最核心的東西,需要依賴HDFS 和Hive 的相關功能[12],雖然SparkSQL 是非常具有潛力的,但目前來說仍然是以Hive Meta 庫作為元數據管理HDFS 作為數據存儲,并且Spark 本身的SQL 解析器不如Hive 同時由于Spark 是基于內存的特性導致建立在Spark 之上的大數據計算集群的成本會大大增加[13],因此從考慮成本和性能穩定性的角度出發,Spark仍然有許多不足之處。由于在大數據處理和查詢時小文件會造成資源的多度占用以及影響查詢效率,有的學者提出采用Sequence?File 作為表存儲格式,而不用TextFile,在一定程度上可以減少小文件的個數,有的學者也提出采用JVM重用機制,該方式是Hadoop中調優參數的內容,對于小文件特別多的場景或者Task 特別多的場景這種調優方式對Hive 的性能有很大的幫助,在這類場景下的大數據執行時間都很短。但不管是SequenceFile 方法還是JVM 重用機制都只是針對小文件過多場景下的優化方法,對于多數情況下的大數據處理問題仍然是在數據量極大且所需要提取出的數據指標過多的場景中進行計算查詢操作,所以根本的問題并沒有得到一個很好的解決。因此本文提出采用增加復雜SQL 的任務并行度、提高集群利用效率和建立中間表的方法。在傳統的Hadoop大數據生態系統基礎上,采用基于Hive 數據庫的編寫SQL 的大數據查詢方法,利用MapReduce 的可以并行執行的特性[14],即將一個復雜的SQL 任務拆分為多個并行執行,不僅可以將一個復雜冗長的SQL 代碼細分為多個,使得每一個代碼塊的分工更加明確,還可以使計算查詢結果一目了然方便閱讀。另外,對于多個并行的SQL 任務有重復查詢某幾個相同的數據指標時,采用建立中間表的方法,也可以大大降低查詢復雜度和查詢時間。
Hadoop 是一個開發和運行處理大規模數據的軟件平臺,是Apache 的一個用Java 語言實現的開源軟件框架,實現通過大量計算機組成的集群對海量數據進行分布式計算。Hadoop 的核心是HDFS和MapReduce以及YARN。

圖1 hadoop核心架構
HDFS是Hadoop體系中數據存儲管理的基礎。它是一個高度容錯的系統,用于在低成本的通用硬件上運行。HDFS 簡化了文件的一致性模型,通過流式數據訪問,提供高吞吐量應用程序數據訪問功能,適合帶有大型數據集的應用程序[15]。MapReduce 源自于Google 的MapReduce 論文,它是一種計算模型,用以進行大數據量的計算。其中Map 對數據集上的獨立元素進行指定的操作,生成鍵值對形式中間結果。Reduce 則對中間結果中相同“鍵”的所有“值”進行規約,以得到最終結果。MapReduce 這樣的功能劃分,非常適合在大量計算機組成的分布式并行環境里進行數據處理。YARN 是一種新的Hadoop 資源管理器,它是一個通用資源管理系統,可謂上層應用提供統一的資源管理和調度,它的引入為集群在利用率、資源統一管理和數據共享等方面帶來了巨大好處。
雖然Hadoop 框架是為大數據處理而設計的,但是如果直接使用Hadoop將面臨學習成本過高以及MapReduce 實現復雜查詢邏輯開發難度太大的問題。因此基于Hive 具有可擴展、高延展、高容錯以及操作接口采用類SQL 語法提供快速開發能力的特性。將Hive 作為大數據處理計算和查詢的工具是非常適合的。
本案例中,以某品牌手機瀏覽器當中推送文章為背景,獲取與手機瀏覽器信息流中文章相關的數據,本文的hive 大數據處理計算和查詢是基于四張大數據庫中的表進行,分別是o2o_ne?whome_log_info 信息流用戶日志表、newhome_valid_user_day 有效用戶中間表、dwm_dvc_ne?whome_device_dura_di 停留時長中間表、 ne?whome_mcc_new_expose_imei_day 新用戶表,總數據量在1Pb 左右。從1Pb 的數據中查詢出信息流DAU、有效用戶數、有效用戶占比、用戶次留、加權內容曝光量等18個指標。
在本案例中,根據指標需求設計出單個任務執行的計算框架。首先從數據源的四張表中根據指標需求編寫出相應代碼,將求得的指標導入到自己創建的Hive表中,最后進入Hive表查看指標結果。

圖2 單任務執行計算框架
在Hive 數據倉庫中以上述四張源數據表作為基礎,根據所需要求的18個數據指標,編寫相應的SQL 操作代碼,最后將所得到的數據指標進行輸出打印。
整個數據處理時長為:

雖然最終能夠查詢出相應的指標結果,但是從執行時長來看,數據處理計算的時間過長,需要進行相應的優化。
當單個查詢SQL 執行時,集群只會分配單個任務資源進行數據的計算處理。因此,可以將一個復雜的SQL 拆分為多個SQL,即將單一任務轉換為多個任務并行執行。當集群處于資源隊列未滿的情況時,這種方法也可以提高集群的利用效率。
本案例采用的策略是根據數據源的四張表將單個復雜的SQL 語句拆分為四個SQL 語句,即將原本單獨執行的任務轉變為四個任務并行執行。即

圖3 多任務執行計算框架
整個數據處理時長為:

數據并行計算處理相較于之前的執行單個SQL 任務時長縮短60%,同時也提高了集群的利用效率。
為了能夠進一步縮短數據計算處理時長,設計了建立中間表的優化方法。針對某一個計算處理多個指標的SQL,通過聚合SQL 中相同的代碼塊提取出中間指標建立中間表,這種方法減少了代碼冗余量的同時也縮短了任務執行時長。

圖4 多任務組合中間表計算框架
整個數據處理時長為

通過在任務并行計算的基礎之上采用建立中間表的方式,相較于之前只通過任務并行優化的方式執行時長上縮短了25%,對比之前沒有采取任何優化措施的執行方式時長上縮短了70%。
該大數據計算處理優化方法采用增加任務并行度與建立中間表組合的方式,通過MapReduce進行數據計算。利用MapReduce 的執行特點,增加任務并行度提高集群使用效率,同時根據SQL的執行特性建立中間表,也大大降低了數據計算的時長。通過實驗得出采用增加任務并行度融合建立中間表的方法相較于僅采用增加任務并行度的方法在計算時間上減少了30%,相較于不做任何優化處理的方式時間上減少了78%,并且提高了集群的使用效率,同時也能夠很好的保證最后得到需要的數據。