我在hive中有以下表格
用户ID,用户名,用户地址,点击次数,展示次数,网页ID,网页名称
我需要通过每个页面的点击次数找到前5位用户[user-id,用户名,用户地址] [page-id,page-name]
据我所知,我们需要先按[page-id,page-name]进行分组,并在每个组中按照[点击次数,展示次数] desc排序,然后只排出前5位用户[user-id,user-name ,每个页面的用户地址,但我发现很难构建查询。
我们如何使用HIve UDF执行此操作?
答案 0 :(得分:15)
修正了答案,修复了@Himanshu Gahlot提到的错误
SELECT page-id, user-id, clicks
FROM (
SELECT page-id, user-id, rank(page-id) as rank, clicks FROM (
SELECT page-id, user-id, clicks FROM mytable
DISTRIBUTE BY page-id
SORT BY page-id, clicks desc
) a ) b
WHERE rank < 5
ORDER BY page-id, rank
请注意,rank()UDAF应用于page-id列,其新值用于重置或增加排名计数器(例如,为每个page-id分区重置计数器)
答案 1 :(得分:11)
从Hive 0.11开始,您可以使用Hive的内置rank()函数并使用Hive's built-in Analytics and Windowing functions使用更简单的语义来完成此操作。可悲的是,我找不到尽可能多的这些例子,但我们真的很有用。使用它们,内置了rank()和WhereWithRankCond,所以你可以这样做:
SELECT page-id, user-id, clicks
FROM (
SELECT page-id, user-id, rank()
over (PARTITION BY page-id ORDER BY clicks DESC) as rank, clicks
FROM my table
) ranked_mytable
WHERE ranked_mytable.rank < 5
ORDER BY page-id, rank
不需要UDF,只有一个子查询!此外,所有等级逻辑都已本地化。
您可以在in this Jira和this guy's blog上找到更多(虽然不够我自己喜欢)的示例。
答案 2 :(得分:9)
您可以使用此处描述的rank()UDF执行此操作:http://ragrawal.wordpress.com/2011/11/18/extract-top-n-records-in-each-group-in-hadoophive/
SELECT page-id, user-id, clicks
FROM (
SELECT page-id, user-id, rank(user-id) as rank, clicks
FROM mytable
DISTRIBUTE BY page-id, user-id
SORT BY page-id, user-id, clicks desc
) a
WHERE rank < 5
ORDER BY page-id, rank
答案 3 :(得分:1)
我们说您的数据如下:
page-id user-id clicks
page1 user1 10
page1 user2 10
page1 user3 9
page1 user4 8
page1 user5 7
page1 user6 7
page1 user7 6
page1 user8 5
page2 user1 20
page2 user2 19
page2 user3 18
以下查询将为您提供:
SELECT page-id, user-id, clicks, rank
FROM (
SELECT page-id, user-id, rank()
over (PARTITION BY page-id ORDER BY clicks DESC) as rank, clicks
FROM your_table
) ranked_table
WHERE ranked_table.rank <= 5
结果:
page-id user-id clicks rank
page1 user1 10 1
page1 user2 10 1
page1 user3 9 3
page1 user4 8 4
page1 user5 7 5
page1 user6 7 5
page2 user1 20 1
page2 user2 19 2
page2 user3 18 3
因此,对于page1,您将获得6个用户,因为具有相同点击次数的用户排名相同。
但是,如果您正在寻找5个用户,并且在多个用户属于同一级别的情况下随机选择。您可以使用以下查询
SELECT page-id, user-id, clicks, rank
FROM (
SELECT page-id, user-id, row_number()
over (PARTITION BY page-id ORDER BY clicks DESC) as rank, clicks
FROM your_table
) ranked_table
WHERE ranked_table.rank <= 5
结果:
page-id user-id clicks rank
page1 user1 10 1
page1 user2 10 2
page1 user3 9 3
page1 user4 8 4
page1 user5 7 5
page2 user1 20 1
page2 user2 19 2
page2 user3 18 3
答案 4 :(得分:-1)
从(选择用户名,用户名,用户地址,页面,点击,row_num()到(。按点击顺序按页面顺序分区)a中选择* * a.row_num <= 5
在选择列时可能会有变化,但是逻辑是正确的。