Unterschiede
Hier werden die Unterschiede zwischen zwei Versionen angezeigt.
| Beide Seiten der vorigen Revision Vorhergehende Überarbeitung Nächste Überarbeitung | Vorhergehende Überarbeitung | ||
| modul:m290_guko:learningunits:lu07:theorie:b_sql_dml [2025/09/28 19:01] – gkoch | modul:m290_guko:learningunits:lu07:theorie:b_sql_dml [2025/09/28 20:07] (aktuell) – gkoch | ||
|---|---|---|---|
| Zeile 1: | Zeile 1: | ||
| - | ====== LU07b – SQL-DML: Daten einfügen, ändern, löschen | + | ====== LU07b – SQL-DML: |
| - | ===== Lernziele ===== | + | |
| - | * Ich kann Daten **einfügen** (// | + | |
| - | * Ich erkenne typische **Fehlerquellen** (fehlendes %%WHERE%%, falsche Datentypen, Schlüsselverletzungen). | + | |
| ===== Einführung ===== | ===== Einführung ===== | ||
| In LU05 haben wir die **DDL** (Data Definition Language) kennengelernt, | In LU05 haben wir die **DDL** (Data Definition Language) kennengelernt, | ||
| Zeile 32: | Zeile 29: | ||
| %%INSERT%% entspricht **Create**, %%SELECT%% entspricht **Read**, %%UPDATE%% entspricht **Update** und %%DELETE%% entspricht **Delete**. | %%INSERT%% entspricht **Create**, %%SELECT%% entspricht **Read**, %%UPDATE%% entspricht **Update** und %%DELETE%% entspricht **Delete**. | ||
| - | Mit DML können wir Daten also gezielt **einfügen**, | ||
| - | ===== INSERT | + | ===== INSERT |
| + | Der Befehl %%INSERT%% fügt neue Datensätze in eine Tabelle ein. Dabei muss angegeben werden, **in welche Spalten** die Werte eingefügt werden. | ||
| - | **Syntax (allgemein: | + | **Syntax (Einzelzeile)** |
| <WRAP center box 80% round>< | <WRAP center box 80% round>< | ||
| INSERT INTO tabellenname (spalte1, spalte2, spalte3) | INSERT INTO tabellenname (spalte1, spalte2, spalte3) | ||
| VALUES (wert1, wert2, wert3); | VALUES (wert1, wert2, wert3); | ||
| </ | </ | ||
| - | __Erklärung: | ||
| - | **Syntax (mehrere Zeilen | + | **Syntax (mehrere Zeilen |
| <WRAP center box 80% round>< | <WRAP center box 80% round>< | ||
| INSERT INTO tabellenname (spalte1, spalte2, spalte3) | INSERT INTO tabellenname (spalte1, spalte2, spalte3) | ||
| VALUES (wert1a, wert2a, wert3a), | VALUES (wert1a, wert2a, wert3a), | ||
| - | | + | |
| - | | + | |
| </ | </ | ||
| - | __Erklärung: | ||
| - | **Syntax (INSERT ... SELECT | + | **Syntax (INSERT ... SELECT)** |
| <WRAP center box 80% round>< | <WRAP center box 80% round>< | ||
| INSERT INTO zieltabelle (spalte1, spalte2, spalte3) | INSERT INTO zieltabelle (spalte1, spalte2, spalte3) | ||
| Zeile 59: | Zeile 53: | ||
| WHERE bedingung; | WHERE bedingung; | ||
| </ | </ | ||
| - | __Erklärung: | ||
| + | --- | ||
| **Variante A: Spalten explizit angeben** | **Variante A: Spalten explizit angeben** | ||
| Zeile 67: | Zeile 61: | ||
| VALUES ('Lost in Translation', | VALUES ('Lost in Translation', | ||
| </ | </ | ||
| - | |||
| - | Ergebnis in Tabelle // | ||
| <WRAP center box 80% round> | <WRAP center box 80% round> | ||
| Zeile 82: | Zeile 74: | ||
| (' | (' | ||
| </ | </ | ||
| - | |||
| - | Ergebnis in Tabelle // | ||
| <WRAP center box 80% round> | <WRAP center box 80% round> | ||
| Zeile 93: | Zeile 83: | ||
| **Variante C: INSERT ... SELECT (Daten aus einer anderen Tabelle übernehmen)** | **Variante C: INSERT ... SELECT (Daten aus einer anderen Tabelle übernehmen)** | ||
| - | Mit %%INSERT ... SELECT%% können Datensätze direkt | + | Mit %%INSERT ... SELECT%% können Datensätze direkt aus einer anderen |
| - | Das ist besonders nützlich, wenn wir Daten aus einer grossen Tabelle (z. B. // | + | Das ist z. B. praktisch, wenn Daten aus // |
| <WRAP center box 80% round>< | <WRAP center box 80% round>< | ||
| Zeile 103: | Zeile 93: | ||
| </ | </ | ||
| - | > **Hinweise:** | + | > **Hinweis:** Mit %%WHERE%% können gezielt nur bestimmte Datensätze übernommen werden (z. B. ab Jahr 2000). |
| - | > Zahlen/Jahr ohne Anführungszeichen, | + | |
| - | > Mit der %%WHERE%%-Bedingung | + | |
| - | + | ||
| - | ===== UPDATE – Daten ändern ===== | + | |
| - | + | ||
| - | **Syntax (mit Filter – empfohlen)** | + | |
| - | <WRAP center box 80% round>< | + | |
| - | UPDATE tabellenname | + | |
| - | SET spalte1 = neuer_wert1, | + | |
| - | WHERE bedingung; | + | |
| - | </ | + | |
| - | __Erklärung: | + | |
| - | + | ||
| - | **Syntax (ohne Filter – mit Vorsicht!)** | + | |
| - | <WRAP center box 80% round>< | + | |
| - | UPDATE tabellenname | + | |
| - | SET spalte1 = neuer_wert1; | + | |
| - | </ | + | |
| - | __Erklärung: | + | |
| - | + | ||
| - | + | ||
| - | Sind bereits Daten in der Tabelle vorhanden, können wir sie mit dem // | + | |
| - | + | ||
| - | **Wichtig: Immer mit %%WHERE%% einschränken!** Das Statement würde auch ohne %%WHERE%%-Clause funktionieren, | + | |
| - | + | ||
| - | <WRAP center box 80% round>< | + | |
| - | -- Regie-Credit korrigieren (gezielt über Primärschlüssel) | + | |
| - | UPDATE favourite_film | + | |
| - | SET director = 'C. Nolan' | + | |
| - | WHERE film_id = 2; | + | |
| - | </ | + | |
| - | + | ||
| - | Ergebnis in Tabelle // | + | |
| - | + | ||
| - | <WRAP center box 80% round> | + | |
| - | ^ film_id ^ title ^ director | + | |
| - | | 1 | Lost in Translation | Sofia Coppola | + | |
| - | | 2 | Inception | + | |
| - | | 3 | Arrival | + | |
| - | </ | + | |
| - | + | ||
| - | **Mehrere Spalten in einem Datensatz auf einmal ändern** | + | |
| - | <WRAP center box 80% round>< | + | |
| - | UPDATE favourite_film | + | |
| - | SET title = ' | + | |
| - | WHERE film_id = 3; | + | |
| - | </ | + | |
| - | + | ||
| - | Ergebnis in Tabelle // | + | |
| - | + | ||
| - | <WRAP center box 80% round> | + | |
| - | ^ film_id ^ title ^ director | + | |
| - | | 1 | Lost in Translation | + | |
| - | | 2 | Inception | + | |
| - | | 3 | Arrival (Extended Cut) | Denis Villeneuve | 2016 | Amy Adams | | + | |
| - | </ | + | |
| - | + | ||
| - | **Semantische Updates (vorsichtig!)** | + | |
| - | <WRAP center box 80% round>< | + | |
| - | -- Alle Filme mit leerem Hauptdarsteller: | + | |
| - | UPDATE favourite_film | + | |
| - | SET star1 = ' | + | |
| - | WHERE star1 IS NULL; | + | |
| - | </ | + | |
| - | + | ||
| - | ===== DELETE – Daten löschen ===== | + | |
| - | + | ||
| - | **Syntax (mit Filter – empfohlen)** | + | |
| - | <WRAP center box 80% round>< | + | |
| - | DELETE FROM tabellenname | + | |
| - | WHERE bedingung; | + | |
| - | </ | + | |
| - | __Erklärung: | + | |
| - | + | ||
| - | **Syntax (ohne Filter – mit Vorsicht!)** | + | |
| - | <WRAP center box 80% round>< | + | |
| - | DELETE FROM tabellenname; | + | |
| - | </ | + | |
| - | __Erklärung: | + | |
| - | + | ||
| - | + | ||
| - | Mit dem // | + | |
| - | + | ||
| - | **Gezielt löschen (über Primärschlüssel)** | + | |
| - | <WRAP center box 80% round>< | + | |
| - | DELETE FROM favourite_film | + | |
| - | WHERE film_id = 1; | + | |
| - | </ | + | |
| - | + | ||
| - | Ergebnis in Tabelle // | + | |
| - | + | ||
| - | <WRAP center box 80% round> | + | |
| - | ^ film_id ^ title ^ director | + | |
| - | | 2 | Inception | + | |
| - | | 3 | Arrival (Extended Cut) | Denis Villeneuve | 2016 | Amy Adams | | + | |
| - | </ | + | |
| - | + | ||
| - | **Mehrere Datensätze in einem Schritt (IN-Liste)** | + | |
| - | <WRAP center box 80% round>< | + | |
| - | DELETE FROM favourite_film | + | |
| - | WHERE film_id IN (2, 3); | + | |
| - | </ | + | |
| - | + | ||
| - | Ergebnis in Tabelle // | + | |
| - | + | ||
| - | <WRAP center box 80% round> | + | |
| - | ^ film_id ^ title ^ director ^ released_year ^ star1 ^ | + | |
| - | | (keine Zeilen mehr vorhanden) ||||| | + | |
| - | </ | + | |
| - | + | ||
| - | ===== TRUNCATE – Tabelle schnell leeren (ohne WHERE) ===== | + | |
| - | %%TRUNCATE%% entfernt **alle** Zeilen einer Tabelle **sehr schnell**. Im Unterschied zu // | + | |
| - | * Keine %%WHERE%%-Bedingung möglich (immer die **ganze** Tabelle). | + | |
| - | * Setzt den AUTO_INCREMENT-Zähler zurück. | + | |
| - | * Kann durch Fremdschlüssel-Constraints blockiert sein. | + | |
| - | * Gilt in vielen Systemen als DDL-Operation (ähnlich wie Tabellendefinitionen). | + | |
| - | + | ||
| - | <WRAP center box 80% round>< | + | |
| - | TRUNCATE TABLE favourite_film; | + | |
| - | </ | + | |
| - | + | ||
| - | ===== Praxis: Sicher arbeiten (SELECT-Variante & Dry-Run) ===== | + | |
| - | Vor jedem //UPDATE// bzw. //DELETE// zuerst mit **SELECT testen**, ob die **gleiche WHERE-Bedingung** die gewünschten Zeilen trifft: | + | |
| - | + | ||
| - | <WRAP center box 80% round>< | + | |
| - | -- Dry-Run: Welche Zeilen wären betroffen? | + | |
| - | SELECT film_id, title FROM favourite_film | + | |
| - | WHERE released_year >= 2020; | + | |
| - | </ | + | |