SQL Server 2005 Fehler bei der Unterabfrage Gruppierung mit
-
06-07-2019 - |
Frage
Verwenden von SQL Server 2005 I Gruppe bin versucht, mit einer Unterabfrage auf eine Fall-Anweisung basiert, aber ich erhalte eine Fehlermeldung ( "Jeder GROUP BY-Ausdruck muss mindestens eine Spalte Referenz enthalten. „). Ich kann ganz einfach um sie herum arbeiten, aber den Fehler jemand erklären kann? Ich habe eine Spalte Bezug auf # header.header bekommt.
create table #header (header int)
create table #detail (header int, detail int)
insert into #header values (1)
insert into #header values (2)
insert into #header values (3)
insert into #detail values (1, 1)
insert into #detail values (2, 1)
--error: Each GROUP BY expression must contain at least one column reference.
select case when exists (select 1 from #detail where #detail.header = #header.header) then 1 else 0 end hasrecords from #header
group by case when exists (select 1 from #detail where #detail.header = #header.header) then 1 else 0 end
--results I want
select hasrecords, count(*) from
(
select case when exists (select 1 from #detail where #detail.header = #header.header) then 1 else 0 end hasrecords from #header
) hasrecords
group by hasrecords
drop table #header
drop table #detail
[Bearbeiten] Hinweis (in Reaktion auf einen Kommentar) korrelierten und nicht-korrelierten Unterabfragen:
--correlated
select header, case when exists (select 1 from #detail where #detail.header = #header.header) then 1 else 0 end hasrecords from #header
--non-correlated
select #header.header, case when count(#detail.header) > 0 then 1 else 0 end hasrecords from #header left join #detail on #header.header = #detail.header group by #header.header
Lösung
Um zu beginnen, wenn wir die volle Fehler geben, sollte es lesen „ Jeder GROUP BY-Ausdruck muss mindestens eine Spalte enthalten, die nicht eine äußere Referenz. “
Um den Fehler zu verstehen, müssen wir klären, was durch eine gemeint ist ‚äußere Referenz‘
(Anmerkung: in diesem Fall ist es nichts mit inneren oder äußeren zu tun Joins)
Die innere und äußere sind in Bezug auf die Hauptabfrage und es ist Subqueries.
In diesem Fall ist die EXISTS
die Unterabfrage und es ist eine korrelierten Unterabfrage, wie sie eine äußere Referenz von #header.header
aufweist, die die äußere Tabelle #header
verweist, während jede Bezugnahme auf #detail
würde als innere Referenzen berücksichtigt werden.
Also im Grunde, weil die CASE
eine korrelierte Unterabfrage verwendet, die die äußere Abfrage verweist, dann ist diese in den Fehlerzustand ausgelöst wird, beacuse diese Fehlermeldung angezeigt, wenn Sie versuchen BY-Klausel nur Ausdrücke in eine Gruppe zu verwenden, die als äußere Referenzen interpretiert .
Unterabfragen können in GROUP BY verwendet werden, aber nicht Subqueries korreliert.
Verwirrend kann der gleiche Fehler durch eine nicht-subqueried, einfachere Abfrage wie
erzeugt werdenselect
case when header=1 then 1
else 0
end headeris1,
'constant'
from #header
group by case when header=1 then 1 else 0 end , 'constant'
oder sogar die Konstante mit einem @variable
ersetzen
Klar wie Schlamm?
Kev
Andere Tipps
Sie sagen es zu einer Gruppe von 1 oder 0, wenn Sie es eine tatsächliche Spalte Gruppe von (Header) geben müssen, nicht Wert.
Also, wenn ich das Verständnis rechts eine Liste der Header fehlen und eine Anzahl ihres Detail Records?
Dies kann für Sie arbeiten?
SELECT DISTINCT h.header, COUNT(d.detail) AS detail_count
FROM #header AS h
LEFT JOIN #detail AS d ON d.header = h.header
GROUP BY h.header, d.detail
Mit Ergebnissen wie ...
header detail_count
1 1
2 1
3 0