[Return result is incorrect] AWS Redshift(Redshift)中Join语句Li



运行带有限制运算符的join语句时查询结果集不正确

子查询之一:

SELECT A3.customerid FROM b1traderecords A3 WHERE A3.customerid  < 100 limit 5
customerid 
-----------
71
88
11
99
44
5 record(s) selected.

包含子查询的连接语句:


select A2.customerid from (SELECT A3.customerid FROM b1traderecords A3 WHERE A3.customerid  < 100 limit 5) A0, (select customerid from b3customerinfo where customerrating > 0.7) A2 where A0.customerid = A2.customerid
customerid 
-----------
88
44
88
9
90
5 record(s) selected.

返回值"9"不在第一个子查询结果中因此,连接结果集似乎不正确。

是bug吗?有什么建议吗?由于

这是预期的行为。Redshift是一个集群,其中不同的计算节点(和片)独立操作。不同行的数据分布在"切片"周围。每一个都有不同的数据。当您在查询上设置这样的小限制时,无论哪个片的数据先到达,都将通过该限制,其余数据将丢失。所以这里有一个"种族"查看哪个片首先返回数据。"谁wins"可以因各种原因而改变。

为了从一个限制查询中获得可预测的结果,你需要一个ORDER BY子句。

################### 更新

在带有LIMIT(或TOP)的子查询中使用order子句,结果变得可预测,但仍然有一些错误。我已经重新创建了你的测试用例,并尝试了这3个版本的查询。

select A2.i1, a1.i1 
from (select top 2 i1 from ffnr_i1 order by i1) A1 
, (select i1 from ffnr_i2 ) A2 
where A1.i1 = A2.i1 and A2.i1 > 20;
select A2.i1, a1.i1 
from (select top 2 i1 from ffnr_i1 order by i1) A1 
, (select i1 from ffnr_i2 ) A2 
where A1.i1 = A2.i1;
select A2.i1, a1.i1 
from (select top 2 i1 from ffnr_i1 order by i1) A1 
, (select i1 from ffnr_i2 ) A2 
where A2.i1 > 20;

以及在查询上运行EXPLAIN。第一个只是将子查询where子句移动到顶层——功能相同。解释计划显示了i1>将20应用于第一个子查询。I1 = a2。i1的要求。

第二个示例产生预期的结果—没有匹配。解释计划的唯一变化是不再有>在任意一个表上的where子句。这一点也不奇怪。

第三个示例也产生了您所期望的结果——A2与A1的前两个值的交叉连接。explain计划的唯一不同之处在于它需要嵌套循环连接,并且现在首先求值A1。

因此,几乎可以看出,它正在执行排除匹配值、连接列上的WHERE原因和另一个表上的隐含WHERE子句的LIMIT。在这种情况下,查询优化器似乎丢失了一些东西。您应该将此作为潜在问题/错误提交给AWS。

我用现代连接语法重写了查询,看看这是否会帮助优化器,但没有运气。我还为A1添加了更多的值(25,26,27,35,36,37),以防WHERE条件在LIMIT之前被应用,但这也没有改变问题。

除非有人看到我错过的东西,我认为这可能是一个红移优化器的错误。