现在的位置: 首页 > 综合 > 正文

Hive中SELECT TOP N的方法(order by与sort by)

2014年09月05日 ⁄ 综合 ⁄ 共 2495字 ⁄ 字号 评论关闭

我想说的SELECT TOP N是取最大前N条或者最小前N条。
Hive
提供了limit关键字,再配合order
by
可以很容易地实现SELECT TOP N
但是在Hiveorder
by
只能使用1reduce,如果表的数据量很大,那么order
by
就会力不从心。
例如我们执行SQLselect
a from ljntest01 order by a limit 10;
控制台会打印出:Number of reduce tasks determined at
compile time: 1
说明启动的reduce数量是编译时确定的。
查看该SQL的执行计划,该SQL只启动1JOB 

假设数据表有1亿条数据,而我们只想取TOP
10
,那对1亿条数据在1reduce中做全排序是非常不合理的。
幸好有sort by,使用sort
by
替换order by就可以解决这个问题:
select a from ljntest01 sort by a limit 10;
首先执行该SQL控制台打印出:Number
of reduce tasks not specified. Estimated from input data size: 1
说明reduce数不是编译时确定的,而是根据输入文件大小动态确定的。
此外查看该SQL的执行计划:

STAGE DEPENDENCIES:
  Stage-1 is a root stage
  Stage-2 depends on stages: Stage-1
  Stage-0 is a root stage 

STAGE PLANS:
  Stage: Stage-1
    Map Reduce
      Alias -> Map Operator Tree:
        ljntest01
          TableScan
            alias: ljntest01
            Select Operator
              expressions:
                    expr: a
                    type: int
              outputColumnNames: _col0
              Reduce Output Operator
                key expressions:
                      expr: _col0
                      type: int
                sort order: +
                tag: -1
                value expressions:
                      expr: _col0
                      type: int
      Reduce Operator Tree:
        Extract
          Limit
            File Output Operator
              compressed: true
              GlobalTableId: 0
              table:
                  input format: org.apache.hadoop.mapred.SequenceFileInputFormat
                  output format: org.apache.hadoop.hive.ql.io.HiveSequenceFileOutputFormat
 

  Stage: Stage-2
    Map Reduce
      Alias -> Map Operator Tree:
        hdfs://hdpnn:9000/group/alidw-cbu/tmp/hive-admin/hive_2012-12-16_01-19-42_893_2878471909568139281/-mr-10002
            Reduce Output Operator
              key expressions:
                    expr: _col0
                    type: int
              sort order: +
              tag: -1
              value expressions:
                    expr: _col0
                    type: int
      Reduce Operator Tree:
        Extract
          Limit
            File Output Operator
              compressed: true
              GlobalTableId: 0
              table:
                  input format: org.apache.hadoop.mapred.TextInputFormat
                  output format: org.apache.hadoop.hive.ql.io.HiveIgnoreKeyTextOutputFormat
 

  Stage: Stage-0
    Fetch Operator
      limit: 10 

sort by可以启动多个reduce,每个reduce做局部排序,但是这对于sort
by limit N
已经够用了。从执行计划中可以看出sort by limit N启动了两个JOB。第一个JOB是在每个reduce中做局部排序,然后分别取TOP
N
。假设启动了Mreduce,第二个JOB再对Mreduce分别局部排好序的总计M
* N
条数据做全局排序,取TOP N,从而得到想要的结果。这样就可以大大提高SELECT
TOP N
的效率。

抱歉!评论已关闭.