我在Amazon Athena(Presto引擎)中有一个表,其中包含一些用户事件,其中有userId(VARCHAR)和ts(timestamp,BIGINT)列。该表很大,有数亿条记录。我想创建一个查询,以按ts列对事件进行排序。我很快发现我不能使用全局ORDER BY ts
,因为这将意味着所有ts值都应存储在单个工作程序节点的内存中,并且会导致内存不足类型错误。
重点是,实际上我不需要全局对这些事件进行排序,如果对单个用户ID进行排序就足够了。我还尝试使用复合查询,其中外部查询获取所有唯一的用户ID,而内部查询使用WHERE userid = current_userid
子句,但是由于我有大约50k不同的用户ID,因此该查询运行的时间过多。 (与JOIN
如here所述,将查询结果汇总在一起也是同样的事情)。我正在寻找一些只对行进行部分排序的sql构造,例如ORDER BY ts OVER (PARTITION BY userid)
(此子句无效)。
答案 0 :(得分:0)
您似乎正在寻找:
ORDER BY RANK() OVER (PARTITION BY userid ORDER BY ts)
但是,我不确定这是否会真正限制工作人员的内存消耗。您需要对此进行测试。
答案 1 :(得分:0)
我很快发现我不能使用全局ORDER BY ts,因为这意味着所有ts值都应存储在单个工作节点的内存中,并且会导致内存不足类型错误
Presto支持分布式排序已有一年多的时间了(由Starburst提供)。分布式排序消除了将所有数据放在一个节点的内存中的需要,因此允许线性缩放以进行排序操作。您拥有的节点越多,可以排序的数据就越多,而不会影响性能(不涉及磁盘/存储)。
我不认为有一种方法可以强迫较早的Presto版本有效地进行总排序,而不必将所有数据都放在一个节点的内存中。因此,除非Athena本地支持分布式排序,否则您无法在用户端进行补偿。
您可以从https://prestosql.io/download.html
获取最新的Presto版本。由于您使用的是AWS,因此可以使用Starburst Presto for AWS在Amazon上进行一键式部署(实际上是“很少点击”)。 (我来自Starburst)。