如何计算小于 Hive 表中特定行的行数?

Posted

技术标签:

【中文标题】如何计算小于 Hive 表中特定行的行数?【英文标题】:How to count the rows which is lesser than a particular row in a Hive table? 【发布时间】:2016-10-02 19:50:06 【问题描述】:

考虑 Hive 中的下表

+------+------+
| id   | res  |
+------+------+
|    1 |   55 |
|    2 |   10 |
|    3 |   89 |
|    4 |  100 |
|    5 |   80 |
|    6 |   55 |
|    7 |   70 |
|    8 |   35 |
|    9 |   46 |
|   10 |   51 |
+------+------+

现在我必须计算小于特定行中 res 值的行数。

对于上表,输出应该是

+------+------+
| id   |count |
+------+------+
|    1 |    4 |
|    2 |    0 |
|    3 |    8 |
|    4 |    9 |  
|    5 |    7 |
|    6 |    4 | 
|    7 |    6 |
|    8 |    1 |
|    9 |    2 |
|   10 |    3 |
+------+------+

【问题讨论】:

【参考方案1】:

您可以尝试RANK OVER 功能。

Hiveql 示例

select
  id,
  res,
  rank() over (ORDER BY res) as rank
from
  my_table
order by
  res

阅读更多 here 和 here。

【讨论】:

???您的查询返回:(2,10,1) (8,35,2) (9,46,3) (10,51,4) (1,55,5) (6,55,5) (7,70,7) (5,80,8) (3,89,9) ( 4,100,10),这不是想要的结果。你运行你的查询了吗?如果我对这个主题感兴趣,请告诉我。 @ozw1z5rd 我能看到的唯一区别是起始索引。 Rank 正在返回从 1 开始的索引。其余一切都相同。 完美!我错过了,它可以在没有叉积的情况下工作。【参考方案2】:

瞧'

+-----+------+
| id  | _c1  |
+-----+------+
| 1   | 4    |
| 2   | 0    |
| 3   | 8    |
| 4   | 9    |
| 5   | 7    |
| 6   | 4    |
| 7   | 6    |
| 8   | 1    |
| 9   | 2    |
| 10  | 3    |
+-----+------+

这很容易而且很疯狂,因为这个查询会产生叉积。当然,对于每一行,您必须找到所有值较小的行,看起来像叉积的东西是隐含的。

SELECT id, SUM(IF ( c.res1 > c.res2, 1 , 0 )) 
FROM ( 
    SELECT id, a.res AS res1, b.res AS res2 
    FROM test_4 AS a 
         INNER JOIN ( 
            SELECT res
            FROM test_4 
         ) b 
) c 
GROUP BY id;

【讨论】:

【参考方案3】:

您可以执行以下操作,但请记住从排名结果中删除 1,因为我们不检查

select
id,
res,
rank() over (ORDER BY res) -1 as rank
FROM point

ORDER BY  id

或者很长的路:

由于 Hive 不支持 CTE(它基于 SQL-92 标准),我们将不得不使用子查询来代替。

假设:我将同时包含 ID 和 RES 的表称为 POINT。

Select id, sum(comparison) as count
From (

Select
a.id,
a.res as res1,
b.res as res2,
Case when a.res > b.res then 1
Else 0
End as comparison

FROM point a
CROSS JOIN point b
) c

GROUP BY id

请测试并告诉我。

【讨论】:

【参考方案4】:

排名可能是要走的路,但这里有一个有趣的选择:

SELECT      mt.id              AS id 
            , mt.res           AS res 
            , COUNT(1) OVER (PARTITION BY NULL ORDER BY mt.res ASC ROWS BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW) - 1   AS cnt
FROM        my_table mt 

【讨论】:

以上是关于如何计算小于 Hive 表中特定行的行数?的主要内容,如果未能解决你的问题,请参考以下文章

SQL/Hive 查询以计算特定值每天的行数

如何使用 jquery 或 javascript 计算具有特定值的行数?

如何加快计算 PostgreSQL 表中的行数?

如何计算 MySQL 表中的行数(PHP PDO)

汇总数据

比较 DB2 和 Hive 的行数