看到这两个摘要后,我很困惑,一个起作用了,另一个却没有。因此,有一个表MyTable
有两列:ID
和Value
代码段1(失败)
/*Find the ID that is related to the maximum value*/
SELECT ID
FROM MyTable AS t /*Here MyTable can be a complex subquery. MyTable is just a placeholder here to show you can't use alias t in the subquery after WHERE*/
WHERE Value = (SELECT MAX(Value) FROM t) /*Get error here: 'Invalid object name t"*/
代码段2(有效)
/*Rank Value column*/
SELECT ID, Value,
(SELECT COUNT(Value) FROM MyTable WHERE Value >= t.Value) AS Rank /*No error raised here for t.Value*/
FROM MyTable AS t
This帖子对此进行了解释
一个人不能从相同范围的子查询中引用别名
但是the same scope
是什么?它能解释代码段2为何起作用的原因吗?我假设还有其他在不同位置使用别名和子查询的可能方式(例如在不同的子句中或以不同的方式嵌套)。那么,将别名与子查询一起使用时,是否要遵循任何通用的防错规则?
(请不要使用类似CTE之类的视图技巧或诸如TOP和LIMIT之类的解决方法)
答案 0 :(得分:1)
您的第一个查询应该可以工作:
SELECT ID
FROM <tablename> t
WHERE Value = (SELECT MAX(Value) FROM <tablename>) ;
您不能使用别名再次引用整个表(这是我认为您要执行的操作,但是在实际示例中,表和别名是t
)。
相反,别名用于表中的列。这样,您就可以将列与正确的表相关联-这样查询就可以明确地实现您的预期。
答案 1 :(得分:1)
让我们看一下第一个查询。
<div class="container">
<div id='div1'></div>
<div id='div2'></div>
<div id='div3'></div>
<div id='div4'></div>
</div>
这将尝试从表别名SELECT ID
FROM MyTable AS t
WHERE Value = (SELECT MAX(Value) FROM t)
中选择。
不允许的。它应该从表或视图中选择。
例如:
t
请注意,这与范围无关。 不使用任何子查询也是不允许的。
例如,由于相同的原因,此操作将失败
SELECT ID
FROM MyTable AS t
WHERE Value = (SELECT MAX(Value) FROM MyTable)
然后我们有第二个查询。
SELECT t1.*, t2.*
FROM MyTable AS t1
JOIN t1 AS t2 ON t2.id = t1.id
这称为相关子查询。
该子查询通过t1sub.Value将外部查询的当前SELECT ID, Value,
(
SELECT COUNT(Value)
FROM MyTable t1sub
WHERE t1sub.Value >= t1out.Value
) AS Rank
FROM MyTable AS t1out
链接到子查询中的表。
它将为外部查询中的每一行重新执行子查询。
关于范围。
这是关于SQL的一部分可以查看和使用的内容。
在先前的SQL中,t1out.Value
别名仅在相关子查询的范围内是已知的。
外部查询甚至不知道子查询中使用的别名t1sub
。
在相关子查询中,可以看到并使用t1sub
。
可以在 db <>小提琴here
上找到一些测试