Zum Anfang:Nein,
SELECT user_id, MAX(salary) FROM users;
ist nicht normgerecht. Sie verwenden eine Aggregatfunktion (MAX
) ohne GROUP BY
Klausel. Dadurch weisen Sie das DBMS an, alle Datensätze zu einer einzigen Ergebniszeile zusammenzufassen. Was sagen Sie nun dem DBMS, dass es in dieser Ergebniszeile anzeigen soll? Das in der Tabelle gefundene maximale Gehalt (MAX(salary)
) und die user_id
. Es gibt jedoch kein das user_id
; es gibt möglicherweise viele verschiedene user_id
in der Tabelle. Dies verstößt gegen den SQL-Standard. MySQL nimmt sich die Freiheit, die nicht aggregierte user_id
zu interpretieren wie beliebig user_id
(willkürlich ausgewählt).
Obwohl die Abfrage ausgeführt wird, ist das Ergebnis normalerweise nicht das gewünschte.
Diese Abfrage:
SELECT user_id, name, MAX(salary) FROM users GROUP BY user_id;
andererseits normgerecht ist. Sehen wir uns noch einmal an, was diese Abfrage macht:Dieses Mal gibt es ein GROUP BY
-Klausel, die dem DBMS mitteilt, dass Sie eine Ergebniszeile pro user_id
wünschen . Für jede user_id
Sie zeigen möchten:das user_id
, die name
, und das maximale salary
. All dies sind gültige Ausdrücke; die user_id
ist die user_id
selbst, das name ist der Benutzername, der der user_id
zugeordnet ist , und das maximale salary
ist das maximale Gehalt des Benutzers. Die nicht aggregierte Spalte name
ist erlaubt, weil es funktional von der gruppierten user_id
abhängig ist . Viele DBMS unterstützen dies jedoch nicht, da es sehr kompliziert werden kann festzustellen, ob ein Ausdruck funktional von der Gruppe abhängig ist oder nicht.
Um den Benutzerdatensatz mit dem maximalen Gehalt anzuzeigen, benötigen Sie eine Begrenzungsklausel. MySQL bietet LIMIT
dafür, was Ihnen die ersten n Zeilen bringen kann. Es handelt sich jedoch nicht um Krawatten.
SELECT * FROM users ORDER BY salary DESC LIMIT 1;
ist
SELECT * FROM users ORDER BY salary FETCH FIRST ROW ONLY;
in Standard-SQL.
Um jedoch mit Bindungen umzugehen, wie in
SELECT * FROM users ORDER BY salary FETCH FIRST ROW WITH TIES;
Sie brauchen eine Unterabfrage in MySQL, weil LIMIT
unterstützt dies nicht:
SELECT * FROM users WHERE salary = (SELECT MAX(salary) FROM users);