本文主要從以下幾個方面展開:
Mars簡介典型場景Demo最佳實踐一、Mars簡介Mars是統一的資料科學平臺,它用來加速傳統的Python資料科學技術棧,在單機中也可以用多核加速,或用分散式來加速。Mars可以部署在單機的分散式叢集,或者Kubernetes和Hadoop Yarn上。
Mars整個框架構建在單機的並行和分散式的這兩個排程的基礎之上,它的資料科學基礎包括三個核心部分,Tensor、DataFrame和Remote。而構建在這個基礎之上的,是Mars Learn模組,它可以相容Scikit-learn API,能簡單地進行更大資料規模的分散式處理。此外,Mars還支援深度學習和機器學習的框架,比如能輕鬆執行TensorFlow、PyTorch等,而且視覺化也可以在Mars上完成。除此之外,Mars還支援了豐富的資料來源。
從傳統Python技術棧到Mars也非常簡單,比如在NumPy和Pandas裡要變成Mars,只需要替換import,然後後面變為延遲執行即可。
普通的Python函式,在呼叫的時候變成mr.spawn來延遲這個過程,最後透過execute來併發執行,不用擔心Mars是執行在單機上還是分散式執行。
而Mars上的TensorFlow大部分也一樣,區別在於main函式部分的變化。最後,我們需要透過run_tensorflow_script的方式把指令碼執行到Mars中。
二、典型場景場景1. CPU和GPU混合計算
在安全和金融領域可以用Mars做CPU和GPU的混合計算,加速現有的工作流。
在這個領域,因為傳統大資料平臺挖掘週期長,資源緊張,需要很久來執行任務,不能達到客戶需求。所以能用Mars DataFrame來加速資料處理,它可以做大規模資料排序,並幫助使用者做高階統計和聚合分析。
另外在安全領域有很多無監督學習的演算法,Mars learn能加速無監督學習,同時拉起分散式深度學習計算加速現有的深度學習訓練。之後,對於某些計算任務也可以利用GPU來加速。
場景2. 可解釋性計算
在廣告領域,在廣告歸因和洞察特徵的解釋演算法中,因為本身計算量大,所以耗時很長。這種情況下,單機加速是比較困難的,基於傳統大資料平臺的分散式也不太靈活,但是透過Mars remote,可以很輕鬆地把計算分佈到幾十臺機器上來加速,達到百倍的效能提升。
場景3. 大規模K-最鄰近演算法
Mars非常廣泛地應用在K-最鄰近演算法中,因為Embedding越來越流行,它讓向量表述實體非常常見。另外,Mars的NearestNeighbors演算法相容scikit-learn,它裡面有暴力演算法,而使用者也需要暴力演算法來進行大規模計算,可以透過多個worker來完成,從而讓效能提升百倍。最後,Mars支援分散式的方式加速Faiss和Proxima,達到千萬級別和上億級別的規模。
三、DemoDemo1. 分析豆瓣電影資料
我們從這個Demo看一下Mars如何加速pandas資料處理及其視覺化。
開始演示之前我們需要安裝Mars。這裡已經建立了Jupyter,然後 pip install pymars。
安裝之後,我們可以到IPython進行驗證,可以看到下面的結果沒有問題,接下來我們就可以進入到Jupyter notebook裡。
我們開始demo。這個資料可以在GitHub地址下載,然後我們用pandas來分析電影的資料,使用ipython memory usage來檢視記憶體使用。
我們的資料主要用到4個CSV檔案,分別是movies、ratings、users和comments。
接下來根據上映日期統計有多少電影釋出。這裡先處理一下資料,讓發行日期只取到年份,去掉日期,並對年份做聚合。
資料出來後,可以用pandas bokeh把圖繪製出來,並透過互動式的方式檢視。
接下來看電影評分的統計。首先把有評分的電影篩選出來,然後把豆瓣評分的數值數量從大到小進行排序。可以看到,最多的評分是6.8分。
同樣,透過pandas bokeh把它畫成柱狀圖,評分差不多呈現正態分佈。
接下來做一個標籤詞雲,看電影哪個標籤詞最多,這裡從movies取出tags,用斜槓分割,然後max words是50。
接下來我們再對電影的Top K進行分析。首先按電影ID進行聚合,求出評價的平均值和個數。然後我們對評價個數進行過濾,從高到低,算出top20的電影。
這是最終的詞雲圖。
接下來我們用Mars做同樣的分析任務。首先是對Mars環境進行部署,然後這裡有5個worker,每個worker是8個CPU和32G記憶體。還是一樣,我們開啟記憶體的監控,做一些import,這裡把import Pandas替換成import mars.dataframe,然後Numpy是import mars.tensor。
隨後我們在SDK裡來建立to mars dataframe,這一步幾乎沒有用到記憶體,最終得到的結果也和之前一樣。
我們用同樣的方式來分析上映日期的電影個數和電影評分。得益於Mars跟Pandas的高度相容,我們也能用Pandas bokeh來呈現結果。
接下來我們用Mars做一個地區的統計,讓它有一個動態的效果。首先我們看一下剛剛計算過的已經released的電影dataframe,然後取1980-2019這幾年的電影,而regions部分可能有多個,所以用斜槓分割開,最後執行排出top10地域電影。
然後我們透過bar chart race來生成動態效果。
Demo2. 豆瓣電影推薦
第二個demo我們會基於剛才豆瓣電影的資料來做一個推薦。我們首先會用TensorFlow Mars來進行訓練,接著用Mars分散式KNN演算法來加速召回計算。
我們先使用單機的技術棧,這個資料已經分成了訓練和測試集,所以我們先to pandas把它下載到本地,接著來對使用者和電影做一個label encode,把它變成一個數字,而不是字串的值。隨後我們對資料進行處理,先按照時間排序,然後按照使用者進行分組,生成分組聚合的結果。
接下來開始訓練,我們需要用TensorFlow訓練出代表user的embedding。之前說過embedding,可以對任一實體用向量描述,所以得到embedding之後,我們在給使用者推薦電影時就可以查詢在這個向量空間裡面跟這個使用者比較接近的電影embedding。
訓練後我們可以儲存向量,這裡的搜尋規模是60萬乘7萬,單機花費了22分鐘,但如果達到千萬乘千萬級別,搜尋耗時要超過800小時,這是不可接受的。
接下來我們看如何用Mars來實現這一過程。首先建立一個Mars叢集,這裡有8個worker。然後和上面一樣,對資料進行預處理,做label encode,按時間排序,按user分組生成分組聚合。
這裡唯一的區別是Mars會自動推斷DataFrame的結果,如果推斷失敗就需要使用者自己提供dtypes和output type。
然後是執行和訓練。這裡TensorFlow可以寫Python檔案,不用寫到notebook裡。
接著我們用Mars的run tensorflow script來跑這個指令碼,然後指定worker是8。可以看到,執行的時間縮小到了23分鐘。同時,我們也拿到了最終的embedding,用Mars做embedding只需1分25秒,比剛剛的時間提升個十倍左右。1400萬乘1400萬也可以穩定在1小時左右,與單機800個小時相比提升是非常巨大的。
四、最佳實踐首先儘量不要使用to pandas和to numpy,因為這會把Mars的分散式資料變成單機的資料,失去了Mars本身的優勢,除非這個操作不能用Mars實現;其次,Mars tensor、DataFrame和learn由於本身受限於API的原因需要自己寫一些函式,所以可以考慮用Mars remote來加速,把操作抽象成函式;第三,Pandas的加速技巧在Mars DataFrame依然適用,比如可以使用更高效的資料型別,可以優先使用內建操作,使用apply取代迴圈。