SQL (Structured Query Language) ist die Abfragesprache relationaler Datenbanken – MySQL, MariaDB, PostgreSQL, SQL Server und SQLite sprechen sie in sehr ähnlicher Form. Die folgenden Bausteine decken den Alltag zu weit über neunzig Prozent ab.
Die Beispieldaten
CREATE TABLE kunden (
id INT PRIMARY KEY,
name VARCHAR(100) NOT NULL,
ort VARCHAR(100),
erstellt DATE
);
CREATE TABLE bestellungen (
id INT PRIMARY KEY,
kunden_id INT NOT NULL REFERENCES kunden(id),
betrag DECIMAL(10,2) NOT NULL,
status VARCHAR(20) NOT NULL
);
SELECT, WHERE, ORDER BY, LIMIT
SELECT id, name, ort
FROM kunden
WHERE ort = 'Lübeck'
AND erstellt >= '2026-01-01'
ORDER BY name ASC
LIMIT 20;
Wichtig: NULL ist kein Wert, sondern „unbekannt". Vergleiche mit = NULL funktionieren nicht – man schreibt where ort IS NULL bzw. IS NOT NULL.
JOINs: Tabellen verbinden
Daten liegen normalisiert in mehreren Tabellen. JOIN führt sie über Schlüssel zusammen.
-- INNER JOIN: nur Kunden MIT Bestellungen
SELECT k.name, b.id AS bestellnr, b.betrag
FROM kunden k
JOIN bestellungen b ON b.kunden_id = k.id;
-- LEFT JOIN: ALLE Kunden, Bestellungen optional
SELECT k.name, COALESCE(SUM(b.betrag), 0) AS umsatz
FROM kunden k
LEFT JOIN bestellungen b ON b.kunden_id = k.id
GROUP BY k.id, k.name;
Der Unterschied ist entscheidend: Ein INNER JOIN verschwindet Kunden ohne Bestellung, ein LEFT JOIN behält sie mit NULL.
Aggregate, GROUP BY und HAVING
SELECT status,
COUNT(*) AS anzahl,
SUM(betrag) AS summe,
AVG(betrag) AS durchschnitt
FROM bestellungen
GROUP BY status
HAVING SUM(betrag) > 1000
ORDER BY summe DESC;
Merksatz für die Reihenfolge: WHERE filtert vor der Gruppierung (einzelne Zeilen), HAVING nach der Gruppierung (Ergebnisgruppen).
Daten ändern
INSERT INTO kunden (id, name, ort, erstellt)
VALUES (101, 'Muster GmbH', 'Lübeck', '2026-09-26');
UPDATE kunden SET ort = 'Hamburg' WHERE id = 101;
DELETE FROM kunden WHERE id = 101;
Vorsicht: Ein UPDATE oder DELETE ohne WHERE trifft alle Zeilen. Vorher mit demselben WHERE ein SELECT ausführen und das Ergebnis prüfen.
Indizes: der wichtigste Hebel für Tempo
Ein Index ist wie das Stichwortverzeichnis eines Buchs: Ohne ihn muss die Datenbank jede Zeile lesen (full table scan).
CREATE INDEX idx_bestellungen_kunden ON bestellungen (kunden_id);
CREATE INDEX idx_kunden_ort ON kunden (ort);
Faustregeln: Indizes auf Spalten, die in WHERE, JOIN und ORDER BY auftauchen; zusammengesetzte Indizes in der Reihenfolge der Filter. Zu viele Indizes kosten Schreibleistung und Speicher – also messen statt raten. Wie man Abfragen analysiert, zeigt die jeweilige EXPLAIN-Ausgabe der Datenbank.
Siehe auch
- SQL-Befehle: Schnellreferenz
- Datenbanken im Wissensbereich
- NoSQL – die Alternative für nicht-relationale Daten