hive udaf

package com.lwz.udaf;

import org.apache.hadoop.hive.ql.exec.UDAF;
import org.apache.hadoop.hive.ql.exec.UDAFEvaluator;
//1.此函数区分一条记录的方法,如果没有group by和where的检索,那么整个表的数据都会被作为一条数据,从而只会init()一次
//然后再把这条数据根据表里面的行数依次进行iterator(),再把iterator()方法返回的结果通过terminatePartial()返回,当再次
//进行iterator()时,结果就会累加,当最后通过terminate()返回,那么此条记录也就处理完成
//2.如果hql中有group by,那么整张表就会被分为几条记录,而且每次处理新记录前都会被init()一次,其余的每个步骤都和上一样
public class MyConcat extends UDAF {
public static class ConcatUDAFEvaluator implements UDAFEvaluator{
  public static class PartialResult{
   String result;
   String delimiter;
  }
  private PartialResult partial;
  //初始化每条记录
  public void init() {
  //每次初始化就是将partial置为空
   partial = null;
  }
  //根据数据的行数轮转调用iterate方法
  public boolean iterate(String id,String name,String deli){
  
   if (name == null||id==null){
//如果传入的参数为空
    return true;
   }
   if (partial == null){
//如果部分结果输出为空,说明是开始读入新的一条记录或者是第一条记录
    partial = new PartialResult();
    //给partial结果赋值
    partial.result = new String("");
    if(  deli == null || deli.equals("") )
    {
    //如果分隔符为空或者为"",给partial赋予默认分隔符","
     partial.delimiter = new String(",");
    }
    else
    {
    //如果分隔符不为空,则把传入的分隔符赋予partial的delimiter
     partial.delimiter = new String(deli);
    }
       
   }
   if ( partial.result.length() > 0 )
   {
//如果partial的结果不为空,则在将结果加上分隔符
    partial.result = partial.result.concat(partial.delimiter);
   }
   //将加上分隔符的结果和新传入进行整合
   partial.result = partial.result.concat(name).concat(id);
  
   return true;
  }
  //返回轮转的结果
  public PartialResult terminatePartial(){
//将每条记录处理完的结果返回
   return partial;
  }
  //合并terminatePartial()返回的结果
  public boolean merge(PartialResult other){
   if (other == null){
    return true;
   }
   if (partial == null){
    partial = new PartialResult();
    partial.result = new String(other.result);
    partial.delimiter = new String(other.delimiter);
   }
   else
   {  
    if ( partial.result.length() > 0 )
    {
     partial.result = partial.result.concat(partial.delimiter);
    }
    partial.result = partial.result.concat(other.result);
   }
   return true;
  }
  //返回最终聚合的结果
  public String terminate(){
   return new String(partial.result);
  }
}
}

•一下两个包是必须的import org.apache.hadoop.hive.ql.exec.UDAF和 org.apache.hadoop.hive.ql.exec.UDAFEvaluator
开发步骤
•函数类需要继承UDAF类,内部类Evaluator实UDAFEvaluator接口
•Evaluator需要实现 init、iterate、terminatePartial、merge、terminate这几个函数
a)init函数实现接口UDAFEvaluator的init函数。
b)iterate接收传入的参数,并进行内部的轮转。其返回类型为boolean。
c)terminatePartial无参数,其为iterate函数轮转结束后,返回轮转数据,terminatePartial类似于hadoop的Combiner。
d)merge接收terminatePartial的返回结果,进行数据merge操作,其返回类型为boolean。
e)terminate返回最终的聚集函数结果。
执行步骤
•执行求平均数函数的步骤
a)将java文件编译成Avg_test.jar。
b)进入hive客户端添加jar包:
hive>add jar /run/jar/Avg_test.jar。
c)创建临时函数:
hive>create temporary function avg_test 'hive.udaf.Avg';
d)查询语句:
hive>select avg_test(scores.math) from scores;
e)销毁临时函数:
hive>drop temporary function avg_test;

你可能感兴趣的:(hive)