UDF開發入門(python udf、hive udf)

開發前的聲明

        udf開發是在數據分析的時候如果內置的函數解析不了的情況下去做的開發,比方說你只想拆分一個字段,拼接一個字段之類的,就不要去搞udf了,這種基本的需求自帶函數完全支持,具體參數可參考文檔:

        http://spark.apache.org/docs/latest/api/sql/search.html?q=cast

        裏面列舉了所有函數的介紹和使用,推薦優先使用官方推出的,因爲自己寫的udf如果對一些異常處理不到位可能會導致數據分析的失敗或者意想不到的情況。但是內置的函數真的滿足不了那就真的沒辦法了,比如在做數據分析的時候經常使用的是ip解析,這個通常就需要自己開發udf了。

udf的分類

        udf平常用的多的也就兩種,一種java寫的,一種python 所寫,下面對這兩種情況分別做個簡單的demo供大家參考。

udf for java(idea)

        1.創建maven工程

            file->project structure->modules->點擊+號->new module->選擇maven

            

            點擊next,填寫groupid(對應包結構)、artifactid(maven倉庫對應的座標)

            source java 代碼,操作如下圖file->project structure,

            

            點擊apply,

        2.開始寫java代碼

            pom文件添加依賴   

  1. <dependency>
  2. <groupId>org.apache.hive</groupId>
  3. <artifactId>hive-exec</artifactId>
  4. <version>1.1.0</version>
  5. </dependency>

                     

  1. import org.apache.hadoop.hive.ql.exec.UDF;
  2.             public class HelloUdf  extends UDF {
  3.                     public String evaluate(String ip) {
  4.                             return ip+ip;
  5.                      }
  6.                     public int evaluate(int ip) {
  7.                             return ip+ip;
  8.                      }
  9.             }

 

       3.編包上傳到hdfs

          在此項目pom文件的路徑下執行mvn clean install

          將target文件中生成的jar文件上傳到hdfs上,路徑自己自定義,我直接上傳到/。

          sudo -u hdfs hdfs dfs -put testudf-1.0-SNAPSHOT.jar /

      4.使用hivesql或者sparksql加載自定義函數

           beeline -u jdbc:hive2://node113.leap.com:10000 -n hive

           create function test.iptonum as 'com.liubl.HelloUdf' using jar 'hdfs:///testudf-1.0-SNAPSHOT.jar';

           (com.liubl.HelloUdf爲代碼類的全路徑自己去粘貼一下)

           (測試sql見圖)

           

udf for python

        python udf入門我就不重新闡述了,我看到有一位同學的博客寫的很清晰,推薦博客

        https://blog.csdn.net/qq_26937525/article/details/54136317

        存在的問題:   

            在數據清洗過程中,如果使用的是TransForm而不是UDF的話,因爲Python是直接向系統申請資源的,而不是像ResourceManager申請資源,故會導致啓動的Python腳本對內存和CPU的使用不可控,尤其是當啓動多個Map時,因爲一個map將啓動一個Python因此,當同時運行的map有幾十個時(測試集羣較小),同時將嘗試啓動相同個數的python(資源夠用的話仍然會啓動幾十個),且此時Map佔用的內存是不會釋放掉的他在一直等待Python的結果,這將導致python可用的資源僅僅是原本分配給系統的很少的資源(注:在安裝Hadoop時,對於單個節點,一般僅僅給系統留出很少的內存,其他的內存全部分給了集羣。例如32G物理內存的節點給系統和dataNode+nodeManager的內存就4-8個G,同時CPU核數也不足節點的一半,剩餘的內存和cpu核數全部劃分給集羣使用。需要注意的是,這裏雖然說是劃分給集羣使用,僅僅是邏輯上的劃分,即規定集羣可以使用的最大的物理內存,超過該內存時MR可以認爲是不會搶佔分配給系統+DataNode+nodeManager的內存的,但是當集羣中沒有MR在執行,即沒有map或者reduce在執行時,劃分給集羣的這部分資源是可以被系統使用的。而若有map和Reduce在執行時,運行map和reduce的JVM的資源不會因爲系統進程需要使用而被釋放掉)所以,所有正在執行的Map一直在等待python的運行結果而沒有釋放掉其自身佔用的資源,故python無法使用分配給集羣的資源而只能使用預留給系統+nodeManager+DataNode的4-8G的內存和很少的cpu核數。因此會導致集羣的資源無法被高效利用。


         綜上,使用Transform(Python)執行效率低的根本原因在於Python是直接向操作系統申請資源,而不是向YARN的ResourceManager申請資源,故而導致節點的資源無法高效組織和被利用。此外,不要輕易使用transform!不要輕易使用transform!不要輕易使用transform

發佈了12 篇原創文章 · 獲贊 26 · 訪問量 3萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章