简体   繁体   English

AWS Athena V2/PrestoDB:在右侧子查询中引用左侧行

[英]AWS Athena V2/PrestoDB: Reference left-hand row in right-hand subquery

I have a usecase where I need to support recursive relationship fetching, with a possible LIMIT clause on each depth of relationship.我有一个用例,我需要支持递归关系获取,每个关系深度都有一个可能的 LIMIT 子句。

Something like:就像是:

SELECT ... FROM artists LIMIT 5
for artist in artists:

    SELECT ... FROM albums WHERE artist_id = artist.id LIMIT 3
    for album in albums:

        SELECT ... FROM tracks WHERE album_id = albums.id LIMIT 2

In Postgres/MySQL etc, you can do this with LATERAL / CROSS APPLY .在 Postgres/MySQL 等中,您可以使用LATERAL / CROSS APPLY来做到这一点。

select *
from
  lateral (
    select ...
    from `Artist`
    limit 5
  ) as `Artist`,

  lateral (
    select ...
    from `Album`
    where `Artist`.`ArtistId` = `Album`.`ArtistId`
    limit 3
  ) as `Album`

Athena says that it supports CROSS JOIN LATERAL : Athena 说它支持CROSS JOIN LATERAL

在此处输入图像描述

However if you try to use this with a correlated subquery, it wigs out但是,如果您尝试将其与相关子查询一起使用,它会假发

Is there any way to emulate the behavior of LATERAL / CROSS APPLY with the variant of SQL that Athena V2 supports?有没有办法用 Athena V2 支持的 SQL 的变体来模拟LATERAL / CROSS APPLY的行为?

  • 在此处输入图像描述

EDIT: Here is some sample data and expected output编辑:这是一些示例数据和预期的 output

{"ArtistId":"1","Name":"AC/DC"}
{"ArtistId":"2","Name":"Accept"}

{"AlbumId":"1","Title":"For Those About To Rock We Salute You","ArtistId":"1"}
{"AlbumId":"2","Title":"Balls to the Wall","ArtistId":"2"}
{"AlbumId":"3","Title":"Restless and Wild","ArtistId":"2"}
{"AlbumId":"4","Title":"Let There Be Rock","ArtistId":"1"}
{"AlbumId":"5","Title":"Third Thing","ArtistId":"2"}
SELECT *
FROM LATERAL (SELECT * FROM Artist LIMIT 2) AS artist,
     LATERAL (SELECT * FROM Album WHERE artist.ArtistId = Album.ArtistId LIMIT 2) AS album
ArtistId艺术家 ID Name姓名 AlbumId专辑编号 Title标题
1 1 AC/DC交流/直流 1 1 For Those About To Rock We Salute You对于那些即将摇滚的人,我们向你致敬
1 1 AC/DC交流/直流 4 4 Let There Be Rock让摇滚
2 2 Accept接受 2 2 Balls to the Wall竭尽全力
2 2 Accept接受 3 3 Restless and Wild躁动狂野

You can simulate this behaviour using row_number window function:您可以使用row_number window function 模拟此行为:

-- sample data
WITH artists(ArtistId,Name) AS (
    VALUES (1,'AC/DC'),
        (2,'Accept'),
        (3,'Behemoth')
),
albums(AlbumId,Title,ArtistId) as (
    VALUES (1,'For Those About To Rock We Salute You',1),
        (2,'Balls to the Wall',2),
        (3,'Restless and Wild',2),
        (4,'Let There Be Rock',1),
        (5,'Third Thing',2)
)

-- query
select a.ArtistId, Name, AlbumId, Title
from (select * from artists limit 2) a
join (
    select *, row_number() over (partition by ArtistId order by AlbumId) rn
    from albums
) al on a.ArtistId = al.ArtistId and al.rn <=2

Output: Output:

ArtistId艺术家 ID Name姓名 AlbumId专辑编号 Title标题
1 1 AC/DC交流/直流 1 1 For Those About To Rock We Salute You对于那些即将摇滚的人,我们向你致敬
1 1 AC/DC交流/直流 4 4 Let There Be Rock让摇滚
2 2 Accept接受 2 2 Balls to the Wall竭尽全力
2 2 Accept接受 3 3 Restless and Wild躁动狂野

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM