patternsqlMajor
Subqueries' aliases same as main queries' aliases
Viewed 0 times
samemainqueriesaliasessubqueries
Problem
I have an SQL query whose aliases are the same as some of its subquery's aliases.
For example:
This works fine, as the subquery's alias seems to hide the main one's.
For example:
select *
from ROOM r
where ...
(
select *
from ROAD r
where ...
)This works fine, as the subquery's alias seems to hide the main one's.
- Will it work that way in all cases?
- Will I ever get undefined results?
- If it's OK to do that, how can I make a reference to the main query's
r?
Solution
It's OK for nested subqueries to use the same aliases as used in the parent query, although it might be a bit confusing for someone reading the code. The name space for aliases on a nested subquery is separate from the name space on the parent. For example the query below has a nested subquery
On a correlated subquery you have access to the parent's aliases, so the aliases must be unique across the parent query and correlated subquery. If we take a correlated subquery such as the one below we have a single, global name space shared between the parent query and the correlated subquery:
The correlated subquery does not have an alias as it does not participate in a join as such1. The references
1 Note that the optimiser may choose to use join operators within the plan behind the scenes, although the actual operation specified is a correlated subquery and not a join against a nested subquery.
b that also has an alias b used within it. This would be potentially confusing to the programmer but fine with the DBMS engine:select a.foo
,b.bar
,b.BarCount
from (select b.bar
,count (*) as BarCount
from BarTable b
join OtherTable o
on b.OtherTableID = o.OtherTableID
group by b.bar) b
join Foobar a
on a.bar = b.barOn a correlated subquery you have access to the parent's aliases, so the aliases must be unique across the parent query and correlated subquery. If we take a correlated subquery such as the one below we have a single, global name space shared between the parent query and the correlated subquery:
select a.foo
,b.bar
from Foobar a
join Bar b
on b.FooBarID = a.FooBarID
where not exists
(select 1
from Bar b2
where b2.BarCategoryID = b.BarCategoryID
and b2.BarDate > b.BarDate)The correlated subquery does not have an alias as it does not participate in a join as such1. The references
b and b2 for bar are both available to the subquery as correlated subqueries share their namespace for aliases with the parent. 1 Note that the optimiser may choose to use join operators within the plan behind the scenes, although the actual operation specified is a correlated subquery and not a join against a nested subquery.
Code Snippets
select a.foo
,b.bar
,b.BarCount
from (select b.bar
,count (*) as BarCount
from BarTable b
join OtherTable o
on b.OtherTableID = o.OtherTableID
group by b.bar) b
join Foobar a
on a.bar = b.barselect a.foo
,b.bar
from Foobar a
join Bar b
on b.FooBarID = a.FooBarID
where not exists
(select 1
from Bar b2
where b2.BarCategoryID = b.BarCategoryID
and b2.BarDate > b.BarDate)Context
StackExchange Database Administrators Q#16516, answer score: 22
Revisions (0)
No revisions yet.