Die Beispieldaten
Die Fragen 1 bis 9 beziehen sich auf diese drei Tabellen. Leere Zellen sind NULL, die Tabelle produkte ist zu Beginn leer.
CREATE TABLE kunden (
id int PRIMARY KEY,
name text NOT NULL,
email text
);
CREATE TABLE bestellungen (
id int PRIMARY KEY,
kunde_id int NOT NULL REFERENCES kunden,
status text NOT NULL
);
CREATE TABLE produkte (
sku text PRIMARY KEY,
preis numeric(10,2) CHECK (preis > 0),
bestand int NOT NULL DEFAULT 0
);
kunden.id name email
1 Anna anna@example.com
2 Ben
3 Cem cem@example.com
4 Dana
5 Eva eva@example.com
bestellungen.id kunde_id status
1 1 offen
2 1 versandt
3 1 offen
4 3 versandt
Teil A: SQL und PostgreSQL
1. Was liefert diese Abfrage?
SELECT count(*), count(email) FROM kunden;
A) 5 und 5
B) 5 und 3
C) 3 und 3
D) Einen Fehler, weil email NULL-Werte enthält
Weiß ich nicht
2. Du willst alle Kunden mit mehr als einer Bestellung. Welche Abfrage ist richtig?
A) SELECT kunde_id, count(*) FROM bestellungen WHERE count(*) > 1 GROUP BY kunde_id;
B) SELECT kunde_id, count(*) FROM bestellungen GROUP BY kunde_id WHERE count(*) > 1;
C) SELECT kunde_id, count(*) FROM bestellungen GROUP BY kunde_id HAVING count(*) > 1;
D) SELECT DISTINCT kunde_id FROM bestellungen WHERE id > 1;
Weiß ich nicht
3. Welche Zahl liefert diese Abfrage?
WITH zahlen AS (SELECT generate_series(1, 6) AS n)
SELECT sum(n) FROM zahlen WHERE n % 2 = 0;
A) 21
B) 9
C) 12
D) 6
Weiß ich nicht
4. Wie viele Zeilen liefert diese Abfrage?
SELECT k.name, b.id
FROM kunden k
LEFT JOIN bestellungen b ON b.kunde_id = k.id
WHERE b.status = 'offen';
A) 2, nur Annas offene Bestellungen
B) 6, Annas zwei offene Bestellungen und die vier übrigen Kunden mit leerem b.id
C) 5, eine Zeile je Kunde
D) 4, eine Zeile je Bestellung
Weiß ich nicht
5. Du willst die Namen aller Kunden, die mindestens eine Bestellung haben, jeden Namen einmal. Was stimmt?
-- Variante 1
SELECT k.name FROM kunden k JOIN bestellungen b ON b.kunde_id = k.id;
-- Variante 2
SELECT k.name FROM kunden k
WHERE EXISTS (SELECT 1 FROM bestellungen b WHERE b.kunde_id = k.id);
A) Beide liefern Anna und Cem.
B) Variante 1 liefert Anna dreimal und Cem einmal, Variante 2 jeden Namen einmal.
C) Variante 2 liefert einen Fehler, weil die Unterabfrage keine Spalte name hat.
D) Variante 1 liefert alle fünf Kunden.
Weiß ich nicht
6. Eine Tabelle gesperrt enthält die Werte 1, 2 und NULL in der Spalte kunde_id. Was liefert diese Abfrage?
SELECT count(*)
FROM generate_series(1, 5) AS g(id)
WHERE id NOT IN (SELECT kunde_id FROM gesperrt);
A) 3
B) 2
C) 0
D) Einen Fehler
Weiß ich nicht
7. Was passiert bei diesem INSERT?
INSERT INTO produkte (sku, preis) VALUES ('A-1', NULL);
A) Fehler, weil der CHECK-Constraint preis > 0 verletzt ist
B) Die Zeile wird eingefügt, preis bleibt NULL.
C) Die Zeile wird eingefügt, preis wird 0.
D) Fehler, weil preis nicht NULL sein darf
Weiß ich nicht
8. Was passiert hier?
DELETE FROM kunden WHERE id = 1;
A) Anna wird gelöscht, ihre Bestellungen auch.
B) Anna wird gelöscht, ihre Bestellungen bleiben mit kunde_id = 1 stehen.
C) Fehler, nichts wird gelöscht, weil Bestellungen auf Anna verweisen.
D) Anna wird gelöscht, kunde_id ihrer Bestellungen wird NULL.
Weiß ich nicht
9. Das Produkt A-1 hat einen Bestand von 5. Wie hoch ist der Bestand danach?
INSERT INTO produkte (sku, preis, bestand) VALUES ('A-1', 9.90, 3)
ON CONFLICT (sku) DO UPDATE SET bestand = produkte.bestand + EXCLUDED.bestand;
A) 3
B) 5
C) 8
D) Fehler, weil A-1 schon existiert
Weiß ich nicht
10. Die Tabelle t ist leer. Du führst in psql nacheinander diese Befehle aus. Wie viele Zeilen hat t danach?
BEGIN;
INSERT INTO t VALUES (1);
SELECT 1/0;
INSERT INTO t VALUES (2);
COMMIT;
A) 2
B) 1, die erste Zeile
C) 1, die zweite Zeile
D) 0
Weiß ich nicht
11. Eine Abfrage auf eine Tabelle mit 100.000 Zeilen zeigt diesen Plan. Was hilft am meisten?
Seq Scan on auftraege (actual rows=10.00 loops=1)
Filter: (kunde_id = 42)
Rows Removed by Filter: 99990
A) VACUUM FULL auftraege
B) Ein Index auf auftraege (kunde_id)
C) SELECT kunde_id statt SELECT *
D) Mehr Arbeitsspeicher für PostgreSQL (shared_buffers)
Weiß ich nicht
12. Was stimmt über EXPLAIN ANALYZE DELETE FROM t;?
A) Es zeigt nur den Plan, gelöscht wird nichts.
B) Es löscht die Zeilen wirklich und zeigt dazu den Plan mit echten Zahlen.
C) Es ist für DELETE nicht erlaubt.
D) Es löscht nur, wenn danach COMMIT folgt, auch ohne BEGIN.
Weiß ich nicht