我想根据某些条件用另一个红移表(表2)的列更新红移表(表1)的两列。运行以下查询时,我收到等值连接谓词错误。
UPDATE schema1.table1
SET col1 = sub.col3,
col2 = sub.col4
FROM (
SELECT a.col1, a.col2, b.col3, b.col4 FROM schema1.table1 a LEFT JOIN schema2.table2 b
ON ((a.col5 > b.col6) AND (a.col5 < b.col7))
)sub;
所以问题是 Redshift 无法确定您要更新哪一行。 应该有一个 WHERE 子句,指示 from-select 的结果如何与正在更新的表相匹配。
这是 Redshift 文档中的示例:
update category set catid=100
from (select event.catid from event left join category cat on event.catid=cat.catid) eventcat
where category.catid=eventcat.catid
and catgroup='Concerts';
即使“from-select”中引用了表“category”,Redshift 也需要 WHERE 子句来对齐结果。 另请注意,“from-select”中对“category”的引用需要使用别名以避免混淆。
现在让我们看看您的查询(已格式化):
UPDATE schema1.table1 SET col1 = sub.col3, col2 = sub.col4
FROM (SELECT a.col1, a.col2, b.col3, b.col4
FROM schema1.table1 a
LEFT JOIN schema2.table2 b
ON ( ( a.col5 > b.col6 ) AND ( a.col5 < b.col7 ) ))sub;
您需要一个 WHERE 子句来允许 Redshift 知道在哪里应用“from-select”的每一行。 这可能很简单
WHERE table1.col1 = sub.col1 AND table1.col2 = sub.col2
但是由于我不知道你的数据模型,所以这可能完全不对。
这里还存在一个危险,即在生成 FROM 结果时使用不等式连接可能会导致大量行和重复更新。
就我个人而言,我发现按照大多数人建议的方式处理等值连接谓词更加困难。我更习惯 sql 语法,因此我发现按照 sql 的方式处理它更直接,方法是预先建立一个确定性的宇宙,然后使用它进行内部联接更新。这样我们就可以避免等值连接错误。
例如,让我们考虑一个更新,您需要针对数据透视表 datalake_active_clients 中缺少的注册表,以更新另一个 dim_clients 中的某个功能。也就是说,在 Redshift 中尝试通过简单地尝试左连接更新来进行更新,但严重失败,导致等连接谓词错误。以下是我避免的方法。
update dim_clients
set active = 0,
date_inactive = getdate()
from dim_clients c
join
(
select c.client_id
from dim_clients c
left join datalake_active_clients dac
on dac.client_id = c.client_id
where dac.client_id is null
) _
on _.client_id = c.client_id
;
它添加了一个额外的层,在其他语言(如 sql)中可以更简单地编码。但是,人们必须利用现有的资源来工作。 这是另一种看待它的方式,以防你更容易理解。
干杯。