开发者社区> 问答> 正文

如何解决使用ODPS聚合函数时执行结果爆炸问题

如何解决使用 ODPS聚合函数时执行结果爆炸问题
知途网 是阿里云在线学习平台,教学答疑中为大家提供使用阿里云产品遇到问题的解决方案,下面 知途网 将为大家讲解一下,如何解决使用 ODPS 聚合函数时执行结果爆炸问题。
ODPS 官方文档上提供了非常丰富的聚合函数,例如 wm_concat,sum,count 等等。
举个例子,会员( user[userid,username] )和购买记录( trade[tradeid,userid,payment,item_title] )是一对多的关系。对这两张表以会员的维度进行聚合组合的记录为 user_trade[userid,username,payment_sum,item_titles],item_titles 这个字段是用 wm_concat(distinct trade.item_title) userid 分组聚合而成的, SQL 如下:
[table=454,#FEFEFE,,1][tr][td]
SELECT userid,username,wm_concat(DISTINCT‘,’,item_title) as item_titles
FROM user u
INNER JOIN trade t ON (u.userid =t.userid)
GROUP BY u.userid,u.username
[/td][/tr][/table]
正常情况下,一个用户不会超过几十笔购买记录。但是,不得不承认林子大了什么鸟都会有,就有这样一些奇葩用户,有上万笔购买记录。导致 ODPS 脚本执行得非常慢,而且最终统计结果超过 ODPS 限定的字符串长度上限而使整个计算过程失败。
解决办法是需要将这些奇葩用户在计算之前先过滤掉,在计算之前先需要生成一张中间表用来表示所有合法的用户 id 集合,中间表 SQL 如下:
[table=454,#FEFEFE,,1][tr][td]
CREATE TABLE tmp_user_filter AS
SELECT tt.userid
FROM(
SELECT userid ,count(t.tradeid) as tcount
FROM user u INNER JOIN user_trade tON(u.userid = t.userid)
GROUP BY u.userid )tt
WHERE tt.tcount < 200
[/td][/tr][/table]
通过这个 SQL 创建了一个临时表,将所有所有交易笔数少于 200 笔交易的用户过筛出来,当然这个 200 这个阀值可以按照业务的需要进行调节。之后在其他脚本中可以与 tmp_user_filter 这个表进行 INNER JOIN ,再用聚合函数统计,那就保证不会聚合爆炸了。
改造后的 SQL 如下:
[table=454,#FEFEFE,,1][tr][td]
SELECT userid,username,wm_concat(DISTINCT‘,’,item_title) as item_titles
FROM user u
INNER JOIN tmp_user_filter f ON (u.userid= f.userid)
INNER JOIN trade t ON (u.userid =t.userid)
GROUP BY u.userid,u.username
[/td][/tr][/table]

以上就是 知途网 为大家整理的解决使用 ODPS 聚合函数时执行结果爆炸问题,更多 ODPS 的使用问题请登录 www.chinamoocs.com 搜索“ 掌握开放式数据处理服务 ODPS ”课程了解。

展开
收起
patricia 2015-11-09 18:09:46 10216 0
2 条回答
写回答
取消 提交回答
  • 我可以回答你一句无可奉告
    2016-04-22 00:32:44
    赞同 展开评论 打赏
  • 学习
    2016-03-13 20:48:03
    赞同 展开评论 打赏
问答排行榜
最热
最新

相关电子书

更多
MaxCompute SQL计算成本调优以及优化方法 立即下载
时序数据库TSDB新功能 - 如何用SQL进行时序查询 立即下载
MySQL查询优化实战 立即下载

相关实验场景

更多