Ich verwende PostgreSQL 9.1 mit einer Ruby on Rails-Anwendung.
Ich versuche, die letzte Version jeder "Gebühr" (in meiner Verlaufstabelle: hist_version_charges) aufzulisten, die zu derselben Projekt-ID gehört (proj_sous_projet_id = 2).
Dadurch verwende ich die Aggregatfunktion max () und wende das Ergebnis auf eine JOIN-Funktion in derselben Tabelle an, in der PostgreSQL nicht berechtigt ist, die Spalten in der SELECT-Klausel zu verwenden, wenn sie nicht in der GROUP BY-Klausel ALTHOUGH mit max () meine natürlich interessiert mich die Zeile mit den Maximalwerten!
Das ist meine Frage:
SELECT h_v_charges.*,
max(last_v.version) as lv
FROM hist_versions_charges h_v_charges
JOIN hist_versions_charges last_v
ON h_v_charges.version = lv
AND h_v_charges.proj_charge_id = last_v.proj_charge_id
GROUP BY last_v.proj_sous_projet_id,
last_v.proj_charge_id
HAVING last_v.proj_sous_projet_id = 2
ORDER BY h_v_charges.proj_charge_id ASC;
Die Fehlermeldung, die ich bekam:
ERROR: column "lv" does not exist
LINE 1: ..._versions_charges last_v ON h_v_charges.version = lv AND h_v...
^
********** Error **********
ERROR: column "lv" does not exist
SQL state: 42703
Character: 147
Ich habe es auch mit "last_v.lv" versucht, aber der Fehler bleibt gleich.
Wenn jemand eine Vorstellung davon hat, was los ist, ist sie mehr als willkommen.
=== UPDATE ===
Laut den Antworten von * a_horse_with_no_name * und Colin 't Hart kam ich schließlich zu folgender Abfrage:
SELECT *
FROM (
SELECT *, max(version) OVER (PARTITION BY proj_charge_id) AS lv
FROM hist_versions_charges
WHERE proj_sous_projet_id = 2) AS hv
WHERE hv.lv = hv.version
ORDER BY hv.proj_charge_id ASC;
Mit einem einzigen ORDER BY geht es etwas schneller.
Ich habe auch die Abfrage mit einer WITH-Klausel versucht. Obwohl "schöner", entsteht eine zusätzliche Bearbeitungsgebühr. Da ich weiß, dass ich die Unterabfrage in Zukunft nicht zweimal oder mehrmals in derselben Hauptabfrage wiederverwenden werde, kann ich eine einfache Unterabfrage problemlos verwenden.
Trotzdem danke an * a_horse_with_no_name * und Colin 't Hart . Ich habe viele Dinge gelernt!
quelle
SELECT
Liste definiert ) in derFROM
Klausel verwendet (eigentlich derON
Teil, der aber immer noch in der FROM-Klausel enthalten ist)!Antworten:
Sie möchten wahrscheinlich so etwas:
Eine möglicherweise (da kein Join erforderlich ist) schnellere Lösung wäre:
Wie Colin betont hat, kann dies auch geschrieben werden als:
quelle
hv
ist ein Alias für die abgeleitete Tabelle (auch bekannt als " Unterabfrage "). Und Sie haben Recht, ich habe den Alias in der abgeleiteten Tabelle vergessen .with clause
. Der große Vorteil besteht darin, dass Sie, wenn Sie in Zukunft entscheiden, dass Sie die Unterabfrage zweimal verwenden müssen, sie namentlich referenzieren können, während Sie beim Unterabfrageansatz die Unterabfrage wiederholen müssen.