我有一张有ip,session_id,hour的桌子。我想聚合这些数据,最后得到一个新的表,该表对每个ip都有一个记录,每个ip都有一个每小时总会话数的数组。
为此,我从子查询开始,
SELECT ip, count(session_id) as sessions, hour
FROM current_table
GROUP BY ip,hour;
这将为每个ip (最多)提供24条记录,并在相应的记录中包含特定时间的会话数。使用这个子查询,我希望填充一个数组(假设hourly_sessions是我正在处理的数组),
hourly_sessions[hour] = sessions
因此,我将得到一个与每个ip和数组索引相关联的数组,表示要检查会话聚合的时间。如果在特定时间内没有会话,我希望它显示0。
如何在蜂箱中使用/不使用UDF来实现这一点?我目前(讨厌和不完整)的方法是使用这样的方法:
collect_set(concat_ws(",",hour,cast(sessions) as STRING))
但是,这需要在每次需要特定的每小时聚合时解析整个数组。
发布于 2015-09-23 11:08:27
首先,我认为您需要研究如何填补数据中的空白。就(ip,小时)对而言。这样做的一种方法是创建一个小时表:
CREATE TABLE HOURS AS Select explode(Array(0,1,2...,23)) as hour;
然后是一个不同的IPS表:
CREATE TABLE IPS AS SELECT distinct ip from current_table;
然后加入他们:
CREATE TABLE IP_HOURS AS SELECT IPS join HOURS;
这为每个IP提供了23个条目。将此与实际计数联系起来:
CREATE TABLE ACTUAL_COUNTS AS
SELECT ip, count(session_id) as sessions, hour
FROM current_table
GROUP BY ip,hour;
CREATE TABLE NO_GAP_COUNTS AS
SELECT a.ip as ip, a.hour as hour, COALESCE(b.sessions, 0) as sessions
FROM IP_HOURS a LEFT JOIN ACTUAL_COUNTS b ON (a.ip = b.ip AND a.hour = b.hour)
您可以按原样使用此表,但如果您确实希望将每小时的计数压缩到一个数组中,以便每个ID有一行,则可以使用Brickhouse "Collect“UDF,因为如果您首先按ip对数据进行排序,它将保持会话计数的顺序。内置在Hive collect_set中并不能保证保持秩序。
https://stackoverflow.com/questions/32732892
复制相似问题