• Hive(12):Hive的函数之自定义函数


    目录

    0. 相关文章链接

    1. 什么是自定义函数

    2. 自定义UDF函数

    3. 自定义UDTF函数


    0. 相关文章链接

     Hive文章汇总 

    1. 什么是自定义函数

    1)Hive 自带了一些函数,比如:max/min等,但是数量有限,自己可以通过自定义UDF来方便的扩展。

    2)当Hive提供的内置函数无法满足你的业务处理需要时,此时就可以考虑使用用户自定义函数(UDF:user-defined function)。

    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;    

    2. 自定义UDF函数

    1)需求:自定义一个UDF实现计算给定字符串的长度,例如:

    1. hive(default)> select my_len("abcd");
    2. 4

    2)创建一个Maven工程Hive

    3)导入依赖

    1. <dependencies>
    2. <dependency>
    3. <groupId>org.apache.hivegroupId>
    4. <artifactId>hive-execartifactId>
    5. <version>3.1.2version>
    6. dependency>
    7. dependencies>

    4)创建一个类

    1. import org.apache.hadoop.hive.ql.exec.UDFArgumentException;
    2. import org.apache.hadoop.hive.ql.exec.UDFArgumentLengthException;
    3. import org.apache.hadoop.hive.ql.exec.UDFArgumentTypeException;
    4. import org.apache.hadoop.hive.ql.metadata.HiveException;
    5. import org.apache.hadoop.hive.ql.udf.generic.GenericUDF;
    6. import org.apache.hadoop.hive.serde2.objectinspector.ObjectInspector;
    7. import org.apache.hadoop.hive.serde2.objectinspector.primitive.PrimitiveObjectInspectorFactory;
    8. /**
    9. * 自定义UDF函数,需要继承GenericUDF类
    10. * 需求: 计算指定字符串的长度
    11. */
    12. public class MyStringLength extends GenericUDF {
    13. /**
    14. *
    15. * @param arguments 输入参数类型的鉴别器对象
    16. * @return 返回值类型的鉴别器对象
    17. * @throws UDFArgumentException
    18. */
    19. @Override
    20. public ObjectInspector initialize(ObjectInspector[] arguments) throws UDFArgumentException {
    21. // 判断输入参数的个数
    22. if(arguments.length !=1){
    23. throw new UDFArgumentLengthException("Input Args Length Error!!!");
    24. }
    25. // 判断输入参数的类型
    26. if(!arguments[0].getCategory().equals(ObjectInspector.Category.PRIMITIVE)){
    27. throw new UDFArgumentTypeException(0,"Input Args Type Error!!!");
    28. }
    29. //函数本身返回值为int,需要返回int类型的鉴别器对象
    30. return PrimitiveObjectInspectorFactory.javaIntObjectInspector;
    31. }
    32. /**
    33. * 函数的逻辑处理
    34. * @param arguments 输入的参数
    35. * @return 返回值
    36. * @throws HiveException
    37. */
    38. @Override
    39. public Object evaluate(DeferredObject[] arguments) throws HiveException {
    40. if(arguments[0].get() == null){
    41. return 0;
    42. }
    43. return arguments[0].get().toString().length();
    44. }
    45. @Override
    46. public String getDisplayString(String[] children) {
    47. return "";
    48. }
    49. }

    5)打成jar包上传到服务器/opt/module/data/myudf.jar

    6)将jar包添加到hive的classpath

    hive (default)> add jar /opt/module/data/myudf.jar;

    7)创建临时函数与开发好的java class关联

    hive (default)> create temporary function my_len as "com.ouyang.hive.MyStringLength";

    8)即可在hql中使用自定义的函数 

    hive (default)> select ename,my_len(ename) ename_len from emp;

    3. 自定义UDTF函数

    1)需求 :自定义一个UDTF实现将一个任意分割符的字符串切割成独立的单词,例如:

    1. hive(default)> select myudtf("hello,world,hadoop,hive", ",");
    2. hello
    3. world
    4. hadoop
    5. hive

    2)代码实现

    1. import org.apache.hadoop.hive.ql.exec.UDFArgumentException;
    2. import org.apache.hadoop.hive.ql.metadata.HiveException;
    3. import org.apache.hadoop.hive.ql.udf.generic.GenericUDTF;
    4. import org.apache.hadoop.hive.serde2.objectinspector.ObjectInspector;
    5. import org.apache.hadoop.hive.serde2.objectinspector.ObjectInspectorFactory;
    6. import org.apache.hadoop.hive.serde2.objectinspector.StructObjectInspector;
    7. import org.apache.hadoop.hive.serde2.objectinspector.primitive.PrimitiveObjectInspectorFactory;
    8. import java.util.ArrayList;
    9. import java.util.List;
    10. public class MyUDTF extends GenericUDTF {
    11. private ArrayList outList = new ArrayList<>();
    12. @Override
    13. public StructObjectInspector initialize(StructObjectInspector argOIs) throws UDFArgumentException {
    14. //1.定义输出数据的列名和类型
    15. List fieldNames = new ArrayList<>();
    16. List fieldOIs = new ArrayList<>();
    17. //2.添加输出数据的列名和类型
    18. fieldNames.add("lineToWord");
    19. fieldOIs.add(PrimitiveObjectInspectorFactory.javaStringObjectInspector);
    20. return ObjectInspectorFactory.getStandardStructObjectInspector(fieldNames, fieldOIs);
    21. }
    22. @Override
    23. public void process(Object[] args) throws HiveException {
    24. //1.获取原始数据
    25. String arg = args[0].toString();
    26. //2.获取数据传入的第二个参数,此处为分隔符
    27. String splitKey = args[1].toString();
    28. //3.将原始数据按照传入的分隔符进行切分
    29. String[] fields = arg.split(splitKey);
    30. //4.遍历切分后的结果,并写出
    31. for (String field : fields) {
    32. //集合为复用的,首先清空集合
    33. outList.clear();
    34. //将每一个单词添加至集合
    35. outList.add(field);
    36. //将集合内容写出
    37. forward(outList);
    38. }
    39. }
    40. @Override
    41. public void close() throws HiveException {
    42. }
    43. }

    3)打成jar包上传到服务器/opt/module/hive/data/myudtf.jar

    4)将jar包添加到hive的classpath下

    hive (default)> add jar /opt/module/hive/data/myudtf.jar;

    5)创建临时函数与开发好的java class关联

    hive (default)> create temporary function myudtf as "com.ouyang.hive.MyUDTF";

    6)使用自定义的函数

    hive (default)> select myudtf("hello,world,hadoop,hive",",");

    注:其他Hive相关系列文章链接由此进 -> Hive文章汇总


  • 相关阅读:
    ASP.NET Core 6框架揭秘实例演示[13]:日志的基本编程模式
    性能、成本与 POSIX 兼容性比较: JuiceFS vs EFS vs FSx for Lustre
    Java中的IO流
    Series (mathematics)
    机器学习之文本挖掘—基于R语言
    高效时代,电商运营如何靠RPA快速提效?
    数据结构与算法(六) 贪心算法
    031-从零搭建微服务-监控中心(一)
    seata分布式事务理论概述
    如何实现服务器时间同步
  • 原文地址:https://blog.csdn.net/yang_shibiao/article/details/126494878