4.2.2 除去多余的操作

操作场景

CREATE TABLE clicks 
(  timestamp date, 
sessionID string, 
url string, 
source_ip string  ) 
STORED as ORC 
tblproperties (“orc.compress” = “SNAPPY”);

比如上边这个表,如果要获取每一个sessionID最新的访问记录,可以这样写:

SELECT clicks.* 
FROM clicks inner join ( select sessionID, max(timestamp) as max_ts 
from clicks 
group by sessionID) latest 
ON clicks.sessionID = latest.sessionID and clicks.timestamp = latest.max_ts;

语句解释:

查看执行计划会发现该语句会产生两个MapReduce,第一个MapReduce生成最新的sessionID信息表,第二MapReduce做一个Join,前面输出的结果与原表进行Join得到最后的结果。

再来看看下边的写法:

SELECT  * 
FROM  (   SELECT  *, 
RANK() over (partition by sessionID, order by timestamp desc) as rank 
FROM clicks 
)  ranked_clicks 
WHERE ranked_clicks.rank=1;

语句解释:

查看执行计划会发现只会有一个MapReduce,该语句将数据读出来对sesssionID进行分组并按时间进行倒序排序,最后过滤出排序后的第一条记录。

比较第一个语句和第二个语句,发现第二个语句减少了一次MapReduce操作,性能自然大幅提升。很明显第一个语句多余执行了一次Join操作,第二语句以分组排序替代了Join,除去了不必要的Join操作,带来了性能的提升。

results matching ""

    No results matching ""