您好,登錄后才能下訂單哦!
這篇文章主要介紹了Hive函數怎么用,具有一定借鑒價值,感興趣的朋友可以參考下,希望大家閱讀完這篇文章之后大有收獲,下面讓小編帶著大家一起了解一下。
1)查看系統自帶的函數 show functions; --289個 2)顯示自帶的函數的用法 desc function upper; 3)詳細顯示自帶的函數的用法 desc function extended upper;
--格式:NVL(value,default_value) value為字段 default_value返回默認值 --案例:當獎金為Null時,用0替代 select ename, comm, sal, nvl(comm,0) from emp;
--格式:case 字段 when 'char' then 1 else 0 end; --案例: +---------------+------------------+--------------+ | emp_sex.name | emp_sex.dept_id | emp_sex.sex | +---------------+------------------+--------------+ | 悟空 | A | 男 | | 大海 | A | 男 | | 宋宋 | B | 男 | | 鳳姐 | A | 女 | | 婷姐 | B | 女 | | 婷婷 | B | 女 | +---------------+------------------+--------------+ +----------+-------+---------+ | dept_id | male | female | +----------+-------+---------+ | A | 2 | 1 | | B | 1 | 2 | +----------+-------+---------+ select dept_id, sum(case sex when '男' then 1 else 0 end) male, sum(case sex when '女' then 1 else 0 end) female from emp_sex group by dept_id; --拓展函數之if: 格式:if(sex='男',1,0) true返回1,false返回0 select dept_id, sum(if(sex='男',1,0)) male, sum(if(sex='女',1,0)) female from emp_sex group by dept_id;
--CONCAT(string A/col, string B/col…)://返回輸入字符串連接后的結果,支持任意個輸入字符串; --CONCAT_WS(separator, str1, str2,...)://它是一個特殊形式的 CONCAT()。第一個參數為參數間的分隔符。 分隔符可以是與剩余參數一樣的字符串。如果分隔符是 NULL,返回值也將為 NULL。這個函數會跳過分隔符參數后的任 何NULL 和空字符串。分隔符將被加到被連接的字符串之間; 注意:CONCAT_WS must be "string or array<string>" --COLLECT_SET(col):函數只接受基本數據類型,它的主要作用是將某字段的值進行去重匯總,產生array類型字段。 --COLLECT_LIST(col):函數只接受基本數據類型,主要作用是將某字段的值進行不去重匯總,產生array類型字段。
數據準備: +---------------+------------------+--------------+ | name | constellation | blood_type | +---------------+------------------+--------------+ | 悟空 | 射手座 | A | | 八戒 | 天秤座 | A | | 路飛 | 射手座 | B | | 娜美 | 射手座 | A | | 女帝 | 天秤座 | A | | 羅賓 | 射手座 | B | +---------------+------------------+--------------+ 需求:把星座和血型一樣的人歸類到一起。結果如下: +-------------+-----------------+ | 天秤座,A | 八戒|女帝 | | 射手座,A | 悟空|娜美 | | 射手座,B | 路飛|羅賓 | +-------------+-----------------+ 按需求查詢數據: SELECT t1.c_b , CONCAT_WS("|",collect_set(t1.name)) FROM ( SELECT NAME ,CONCAT_WS(',',constellation,blood_type) c_b FROM person_info )t1 GROUP BY t1.c_b
--Split(str, separator):將字符串按照后面的分隔符切割,轉換成字符array。 --EXPLODE(col):將hive一列中復雜的array或者map結構拆分成多行。 --LATERAL VIEW 用法:LATERAL VIEW udtf(expression) tableAlias AS columnAlias 解釋:lateral view用于和split, explode等UDTF一起使用,它能夠將一行數據拆成多行數據,在此基礎上可以對拆 分后的數據進行聚合。 lateral view首先為原始表的每行調用UDTF,UTDF會把一行拆分成一或者多行,lateral view再把結果組合,產生一 個支持別名表的虛擬表。
數據準備: +------------------+--------------------------+ | movie | category | +------------------+--------------------------+ | 《疑犯追蹤》 | 懸疑,動作,科幻,劇情 | | 《Lie to me》 | 懸疑,警匪,動作,心理,劇情 | | 《戰狼2》 | 戰爭,動作,災難 | +-----------------+---------------------------+ 需求:將電影分類中的數組數據展開。結果如下 《疑犯追蹤》 懸疑 《疑犯追蹤》 動作 《疑犯追蹤》 科幻 《疑犯追蹤》 劇情 《Lie to me》 懸疑 《Lie to me》 警匪 《Lie to me》 動作 《Lie to me》 心理 《Lie to me》 劇情 《戰狼2》 戰爭 《戰狼2》 動作 《戰狼2》 災難 按需求查詢數據: SELECT movie,category_name FROM movie_info lateral VIEW explode(split(category,",")) movie_info_tmp AS category_name ;
--OVER():指定分析函數工作的數據窗口大小,這個數據窗口大小可能會隨著行的變化而變化。 --CURRENT ROW:當前行 --n PRECEDING:往前n行數據 --n FOLLOWING:往后n行數據 --UNBOUNDED:無邊界 --UNBOUNDED PRECEDING 前無邊界,表示從前面的起點, --UNBOUNDED FOLLOWING 后無邊界,表示到后面的終點 --LAG(col,n,default_val):往前第n行數據 --LEAD(col,n, default_val):往后第n行數據 --FIRST_VALUE (col,true/false):當前窗口下的第一個值,第二個參數為true,跳過空值 --LAST_VALUE (col,true/false):當前窗口下的最后一個值,第二個參數為true,跳過空值 --NTILE(n):把有序窗口的行分發到指定數據的組中,各個組有編號,編號從1開始,對于每一行,NTILE返回此行所屬 的組的編號。注意:n必須為int類型。
數據準備:name,orderdate,cost jack,2017-01-01,10 tony,2017-01-02,15 jack,2017-02-03,23 tony,2017-01-04,29 jack,2017-01-05,46 jack,2017-04-06,42 tony,2017-01-07,50 jack,2017-01-08,55 mart,2017-04-08,62 mart,2017-04-09,68 neil,2017-05-10,12 mart,2017-04-11,75 neil,2017-06-12,80 mart,2017-04-13,94 需求: (1)查詢在2017年4月份購買過的顧客及總人數 (2)查詢顧客的購買明細及月購買總額 (3)上述的場景, 將每個顧客的cost按照日期進行累加 (4)查詢顧客購買明細以及上次的購買時間和下次購買時間 (5)查詢顧客每個月第一次的購買時間 和 每個月的最后一次購買時間 (6)查詢前20%時間的訂單信息 按需求查詢數據: (1)查詢在2017年4月份購買過的顧客及總人數 select name,count(name) over() Person_num from business where month(orderdate)=4 //或者where substring(orderdate,1,7)='2017-04' group by name; (2)查詢顧客的購買明細及月購買總額 select name,orderdate,cost, sum(cost) over(partition by name,month(orderdate)) month_amount from business; (3)將每個顧客的cost按照日期進行累加 select name,orderdate,cost, sum(cost) over(partition by name order by orderdate //rows between unbounded preceding and current row) accu_cost --默認 可以不加 from business; 注意: rows必須跟在Order by子句之后,對排序的結果進行限制,使用固定的行數來限制分區中的數據行數量 order by子句后面不加 rows between and,默認為rows between unbounded preceding and current row (4)查詢顧客購買明細以及上次的購買時間和下次購買時間 select name,orderdate,cost, lag(orderdate,1,'1970-01-01') over(partition by name order by orderdate) last_date, lead(orderdate,1,'1970-01-01') over(partition by name order by orderdate) next_date from business; (5)查詢顧客每個月第一次的購買時間 和 每個月的最后一次購買時間 select name,orderdate,cost, first_value(orderdate) over(partition by name,month(orderdate) order by orderdate rows between unbounded preceding and unbounded following) first_date, last_value(orderdate) over(partition by name,month(orderdate) order by orderdate rows between unbounded preceding and unbounded following) last_date from business; (6)查詢前20%時間的訂單信息 select * from ( select name, orderdate, cost, ntile(5) over (order by orderdate) date_rank from business )t1 where t1.date_rank=1;
--RANK() 排序相同時會重復(考慮并列,會跳號),總數不會變 --DENSE_RANK() 排序相同時會重復(考慮并列,不跳號),總數會減少 --ROW_NUMBER() 會根據順序計算(不考慮并列,不跳號,行號)
數據準備: name subject score 孫悟空 語文 87 孫悟空 數學 95 孫悟空 英語 68 路飛 語文 94 路飛 數學 56 路飛 英語 84 柯南 語文 64 柯南 數學 86 柯南 英語 84 艾倫 語文 65 艾倫 數學 85 艾倫 英語 78 需求:計算每門學科成績排名。 按需求查詢數據: select name,subject,score, rank() over(partition by subject order by score desc) rp, dense_rank() over(partition by subject order by score desc) drp, row_number() over(partition by subject order by score desc) rmp from score; 結果: name subject score rp drp rmp 孫悟空 數學 95 1 1 1 柯南 數學 86 2 2 2 艾倫 數學 85 3 3 3 路飛 數學 56 4 4 4 柯南 英語 84 1 1 1 路飛 英語 84 1 1 2 艾倫 英語 78 3 2 3 孫悟空 英語 68 4 3 4 路飛 語文 94 1 1 1 孫悟空 語文 87 2 2 2 艾倫 語文 65 3 3 3 柯南 語文 64 4 4 4
1)Hive 自帶了一些函數,比如:max/min等,但是數量有限,自己可以通過自定義UDF來方便的擴展。 2)當Hive提供的內置函數無法滿足你的業務處理需要時,此時就可以考慮使用用戶自定義函數 3)根據用戶自定義函數類別分為以下三種: --UDF(User-Defined-Function) 一進一出 --UDAF(User-Defined Aggregation Function) 用戶自定義聚合函數,多進一出 類似于:count/max/min --UDTF(User-Defined Table-Generating Functions) 用戶自定義表生成函數,一進多出 如lateral view explode() 4)官方文檔地址 https://cwiki.apache.org/confluence/display/Hive/HivePlugins 5)編程步驟: ①繼承Hive提供的類 org.apache.hadoop.hive.ql.udf.generic.GenericUDF org.apache.hadoop.hive.ql.udf.generic.GenericUDTF; ②實現類中的抽象方法 ③在hive的命令行窗口創建函數 添加jar add jar linux_jar_path 創建function create [temporary] function [dbname.]function_name AS class_name; ④在hive的命令行窗口刪除函數 drop [temporary] function [if exists] [dbname.]function_name;
需求:自定義一個UDF實現計算給定字符串的長度,例如: select my_len("abcd"); 4 1)創建一個Maven工程Hive 2)導入依賴 <dependencies> <dependency> <groupId>org.apache.hive</groupId> <artifactId>hive-exec</artifactId> <version>3.1.2</version> </dependency> </dependencies>
3)創建一個類 /** * 一、自定義UDF函數,需要繼承GenericUDF類 * 需求: 計算指定字符串的長度 */ public class Mylength extends GenericUDF { /** * 二、初始化方法,里面要做三件事 * 1.約束函數傳入參數的個數 * 2.約束函數傳入參數的類型 * 3.約束函數返回值的類型 * @param arguments 函數傳入參數的類型 * @return * @throws UDFArgumentException */ public ObjectInspector initialize(ObjectInspector[] arguments) throws UDFArgumentException { //1.約束函數傳入參數的個數 if (arguments.length != 1){ throw new UDFArgumentLengthException("Input args num error!!!"); } //2.約束函數傳入參數的類型 if (!arguments[0].getCategory().equals(ObjectInspector.Category.PRIMITIVE)) //第一個參數:第幾個數據 //第二個參數 :錯誤信息 throw new UDFArgumentTypeException(0,"Input args type error!!!"); //3.約束函數返回值的類型 return PrimitiveObjectInspectorFactory.javaIntObjectInspector; } /** * 函數邏輯處理方法 * @param arguments 函數傳入參數的值 * @return * @throws HiveException */ public Object evaluate(DeferredObject[] arguments) throws HiveException { //獲取函數傳入參數的值 Object o = arguments[0].get(); //將object轉換為字符串 int length = o.toString().length(); //因為在上面的初始化方法里面已經對函數返回值類型做了約束,必須返回一個int類型 //所以我們要在這個地方直接返回length return length; } /** * 返回顯示字符串方法,這個方法不用管,直接返回一個空字符串 * @param children * @return */ public String getDisplayString(String[] children) { return ""; } }
4)創建臨時函數 ①打成jar包上傳到服務器/opt/module/hive/datas/myudf.jar ②將jar包添加到hive的classpath,臨時生效 hive (default)> add jar /opt/module/hive/datas/myudf.jar; ③創建臨時函數與開發好的java class關聯 hive (default)> create temporary function my_len as "com.atguigu.test.Mylength"; ④即可在hql中使用自定義的臨時函數 hive (default)> select ename,my_len(ename) ename_len from emp; ⑤刪除臨時函數 hive (default)> drop temporary function my_len; --注意:臨時函數只跟會話有關系,跟庫沒有關系。只要創建臨時函數的會話不斷,在當前會話下,任意一個庫都可以 使用,其他會話全都不能使用。
5)創建永久函數 ①在$HIVE_HOME下面創建auxlib目錄(固定名稱不能更改) mkdir auxlib ②將jar包上傳到$HIVE_HOME/auxlib下,然后重啟hive ③創建永久函數 hive (default)> create function my_len2 as " com.atguigu.test.Mylength"; ④即可在hql中使用自定義的永久函數 hive (default)> select ename,my_len2(ename) ename_len from emp; ⑤刪除永久函數 hive (default)> drop function my_len2; --注意:永久函數跟會話沒有關系,創建函數的會話斷了以后,其他會話也可以使用。 永久函數創建的時候,在函數名之前需要自己加上庫名,如果不指定庫名的話,會默認把當前庫的庫名給加上。 永久函數使用的時候,需要在指定的庫里面操作,或者在其他庫里面使用的話加上 庫名.函數名
感謝你能夠認真閱讀完這篇文章,希望小編分享的“Hive函數怎么用”這篇文章對大家有幫助,同時也希望大家多多支持億速云,關注億速云行業資訊頻道,更多相關知識等著你來學習!
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。