28.12.2012 Aufrufe

A RS - of the AG Database-Systems

A RS - of the AG Database-Systems

A RS - of the AG Database-Systems

MEHR ANZEIGEN
WENIGER ANZEIGEN

Sie wollen auch ein ePaper? Erhöhen Sie die Reichweite Ihrer Titel.

YUMPU macht aus Druck-PDFs automatisch weboptimierte ePaper, die Google liebt.

Datenbanksysteme<br />

Bernhard Seeger<br />

Fachbereich Ma<strong>the</strong>matik und Informatik<br />

Philipps-Universität Marburg<br />

Email: seeger@informatik.uni-marburg.de<br />

Tel.: 06421-28 21526<br />

Dieses “Skript” ist nur als eine Orientierungshilfe zur Vorlesung Datenbanksysteme. Die Kopien<br />

entsprechen zu einem großen Teil den Folien, die in den Vorlesungsstunden aufgelegt und erläutert<br />

werden.<br />

Seite 1


Organisation<br />

� Vorlesung<br />

– Mi. 12:00-14:00 HG 007, Fr. 8:00-10:00 HG 007<br />

� Übung<br />

– Übungsleiter: Daniar Achakeyev<br />

– Übungsblätter<br />

– Ausgabe des Übungsblatts: in der Vorlesung am Freitag<br />

– Abgabe der Übungen in der kommenden Vorlesung am Freitag<br />

– Korrektur der Aufgaben<br />

– Übungstermine: Di 14-16 und Di 16-18 jeweils im HS I<br />

� Benoteter Schein:<br />

– 50% der Übungsaufgaben + Klausur<br />

– Note des Moduls = Note der Klausur<br />

� Web-Seite:<br />

– http://dbs.ma<strong>the</strong>matik.uni-marburg.de/teaching/vl/DBS1/09SS/<br />

Seite 2


Basisliteratur<br />

Literaturliste<br />

� A. Kemper, A. Eikler: “Datenbanksysteme. Eine Einführung”, Oldenbourg, 2008 (6. Auflage).<br />

� G. Saake, A. Heuer: “Datenbanken Konzepte und Sprachen”, mitp. 2008.<br />

� G. Vossen: “Datenmodelle, Datenbanksprachen und Datenbankmanagement-Systeme”,<br />

Oldenbourg, 2008.<br />

� Jeffrey D. Ullman, Jennifer D. Widom: A First Course in <strong>Database</strong> <strong>Systems</strong>, Prentice Hall,<br />

2001.<br />

� Ramez A. Elmasri, Shamkant B. Nava<strong>the</strong>: Grundlagen von Datenbanksystemen, Pearson<br />

Studium 2005.<br />

� Gunter Saake, Kai-Uwe Sattler: "Datenbanken und Java. JDBC, SQLJ und ODMG", dpunkt<br />

Verlag, 2003.<br />

Spezialliteratur<br />

� Gerhard Weikum, Gottfried Vossen: Transactional Information <strong>Systems</strong>: Theory, Algorithms,<br />

and <strong>the</strong> Practice <strong>of</strong> Concurrency Control, Morgan Kaufmann, 2001.<br />

� Serge Abiteboul, Richard Hull, Victor Vianu: Foundations <strong>of</strong> <strong>Database</strong> <strong>Systems</strong>, Addison-<br />

Wesley, 1995.<br />

Seite 3


Wichtige Zeitschriften und Konferenzen<br />

Zeitschriften:<br />

� ACM Transactions on <strong>Database</strong> <strong>Systems</strong> (TODS)<br />

� The VLDB Journal<br />

� IEEE Transactions on Knowledge and <strong>Database</strong> Engineering (TKDE)<br />

� Information <strong>Systems</strong><br />

Wichtige Konferenzen:<br />

� Int. Conf. on Very Large Data Bases (VLDB)<br />

� ACM SIGMOD Int. Conf. on Management <strong>of</strong> Data (SIGMOD)<br />

� ACM SIGACT-SIGMOD Principles <strong>of</strong> <strong>Database</strong> <strong>Systems</strong> (PODS)<br />

� IEEE Int. Conf. on Data Engineering (ICDE)<br />

� Int. Conf. on Extending <strong>Database</strong> Technology (EDBT)<br />

Seite 4


Vorläufiges Inhaltsverzeichnis<br />

1. Einführung<br />

2. Konzeptioneller Datenbankentwurf<br />

3. Relationales Modell<br />

Relationale Algebra, Tupelkalkül, Erweiterte Relationale Algebra<br />

4. SQL: Die relationale Datenbanksprache<br />

5. Anwendungsprogrammierung<br />

6. Entwurfs<strong>the</strong>orie<br />

7. Transaktionskonzepte u. Fehlerbehandlung<br />

8. Indexstrukturen<br />

9. Anfrageverarbeitung<br />

10.Data Warehouse<br />

Seite 5


1. Einführung<br />

Einführung<br />

� Datenbanksysteme (DBS) werden genutzt zur rechnergestützten Verwaltung großer<br />

Datenbestände, die auf nichtflüchtigen Speichermedien abgelegt werden.<br />

– Daten liegen i. A. auf großen Magnetplattenspeicher<br />

� Datenbanksystem besteht aus<br />

– Datenbankverwaltungssystem (engl. database management system, DBMS)<br />

Dahinter verbirgt sich die S<strong>of</strong>tware zur Verwaltung von Daten.<br />

– Datenbank<br />

Darunter versteht man die zu verwaltenden Daten und andere Hilfsdaten (z. B. Indexe und<br />

Metadaten). Eine Datenbank stellt eine logische Einheit dar.<br />

Benutzer<br />

Dateneingabe<br />

Anfragen Antworten<br />

<strong>Database</strong> Management System (DBMS)<br />

Datenbank<br />

Seite 6


Anwendungen von Datenbanksystemen<br />

� Implementierung anwendungsspezifischer Informationssysteme durch Datenbanksysteme<br />

– Beispiel: SAP<br />

� Klassische Anwendungen<br />

– Bankinformationssystem:<br />

Verwaltung der Kunden, ihre Konten, …<br />

– Versicherungsinformationssystem:<br />

Verwaltung der Kunden, ihre Verträge, …<br />

� Neuartige Anwendungen<br />

– Biologie:<br />

Gen-Datenbanken<br />

– Geo-Datenbanken<br />

Kataster, Leitungsnetzwerke wie z. B. bei Energieversorger<br />

– Content-Managementsysteme<br />

Text-Dokumente wie z. B. Artikel, Zeitschriften, Bücher<br />

– Multimedia-Informationssysteme:<br />

Bilder, Videos<br />

Einführung<br />

Seite 7


Einführung<br />

Als es noch keine Datenbanksysteme gab, …<br />

� Entwicklung von DBS setzte erst in den frühen 60er Jahre ein. Zuvor wurden vornehmlich<br />

einfache Dateisysteme benutzt.<br />

Beispiel für die Datenverarbeitung in einer Versicherung:<br />

� Drei Kundenberater Alfred, Beatrice und Carlo, die je nach Art des<br />

Versicherungstyps Kunden betreuen.<br />

� Jeder der Kundenberater benutzt für den Zugriff auf die<br />

Kundendaten ein eigenentwickeltes Programm<br />

� Jeder Berater hat seine eigene Kundendatei<br />

KB Alfred<br />

KB Beatrice<br />

KB Carlo<br />

Programm<br />

KundenVonA<br />

Programm<br />

KundenVonB<br />

Programm<br />

KundenVonC<br />

Seite 8


Anwendungsprogramme<br />

� Anwendungsprogramm (AWP)<br />

– Ein Programm, das direkt durch den Benutzer oder eine spezifische<br />

Anwendungskomponente aufgerufen wird.<br />

� Beispiel (statt wie früher üblich Cobol oder PL1 benutzen wir Java)<br />

import java.io.*;<br />

class Anfrage1 {<br />

public static void main(String[] args) throws IOException {<br />

int index = Integer.parseInt(args[0]);<br />

float tmp, limit = Integer.parseFloat(args[1]);<br />

}<br />

}<br />

Einführung<br />

RandomAccessFile raf = new RandomAccessFile("feld.myf", "r");<br />

while (index*4 < raf.length()) {<br />

raf.seek(index * 4);<br />

index++;<br />

tmp = raf.readFloat();<br />

if (tmp > limit)<br />

System.out.println(raf.readFloat());<br />

raf.close();<br />

Seite 9


Probleme der frühen Datenverarbeitung<br />

Einführung<br />

� Direkte Erzeugung und Verarbeitung der Daten erfolgte im AWP unter Verwendung von<br />

Dateien<br />

– kein standardisiertes Speicherungsformat<br />

– hoher Aufwand beim Austausch von Daten verschiedener Benutzern<br />

– mehrfache und unkoordinierte Verwaltung der Daten<br />

– häufige Inkonsistenzen im Datenbestand<br />

– hoher Aufwand bei der Verknüpfung von Daten aus mehreren Dateien<br />

� Zugriff auf Daten erfolgt explizit im AWP<br />

– hoher Aufwand für die Entwicklung einer großen Anzahl maßgeschneiderter, aber auch<br />

unflexibler Programme<br />

– Programmcode zur Optimierung des Datenzugriffs durch den Anwender<br />

� Dateninkonsistenzen bei gleichzeitigem Zugriff durch mehrere Benutzer<br />

� Unzureichende Möglichkeiten beim Datenschutz<br />

Seite 10


Anforderungen an ein Datenbanksystem<br />

Gemeinsame Datenbasis und Mehrbenutzerbetrieb<br />

� Gemeinsam genutzte, persistente Datenbasis auf dem Externspeicher<br />

– Zugriff der Benutzer und der AWP auf einen gemeinsam verwalteten Datenbestand<br />

� Kontrollierte Datenredundanz<br />

– Vermeidung von Kopien derselben Daten durch integrierte Verwaltung aller Daten.<br />

� Mehrbenutzerbetrieb<br />

– Gleichzeitiger Zugriff mehrerer Benutzer auf ihre Daten<br />

– Virtuelles Einbenutzersystem<br />

Korrek<strong>the</strong>it und Qualität der Daten<br />

Einführung<br />

� Datenintegrität<br />

– Unterstützung von Integritätsbedingungen zur Gewährleistung der Korrek<strong>the</strong>it und<br />

Vollständigkeit der Daten<br />

– Automatische Überprüfung der Bedingungen beim Einfügen, Ändern und Löschen der<br />

Daten<br />

Seite 11


Einführung<br />

� Datenkonsistenz<br />

– Automatische Sicherstellung der Datenkonsistenz auf Basis der Integritätsbedingungen<br />

� Datenschutz<br />

– Zugriffskontrolle durch Au<strong>the</strong>ntisierung und Verschlüsselung<br />

– Schutz der Datenbank vor nicht-autorisierten Zugriff<br />

� Fehlerbehandlung<br />

– Schutz vor den Auswirkungen von Systemfehlern<br />

– Wiederanlauf des <strong>Systems</strong> (Recovery): automatisches Wiederherstellen des zuletzt<br />

aktuellen, konsistenten Datenbankzustands mittels von Log-Dateien<br />

– Anlegen von Sicherungskopien für den Fall der Zerstörung eines Speichermediums<br />

S<strong>of</strong>twareentwicklung mit DBMS<br />

� Schnelle Entwicklung von neuen Anwendungen<br />

– unter Ausnutzung einer mächtigen Infrastruktur<br />

� Flexible und schnelle Anpassung von Programmen bei Änderungen im Datenbestand<br />

– Verteilung der Daten über mehrere Platten<br />

– Änderung der Speicherorganisation<br />

– Änderung des Typs der Daten<br />

Seite 12


� Bereitsstellung verschiedener Benutzerschnittstellen<br />

– Ad-hoc Anfragesprachen für interaktive Benutzer<br />

– Programmierschnittstellen für die Erstellung von AWP<br />

– Menügesteuerte, einfach zu benutzende Schnittstelle (GUI)<br />

– Spezieller Zugang für Administrator (z. B. zur Datendefinition)<br />

Performanz<br />

Einführung<br />

� Schneller Datenzugriff<br />

– Mächtige Sammlung von Werkzeugen zur effizienten Speicherung und<br />

Anfrageverarbeitung externer Datenquellen.<br />

– Indexstrukturen für große Datenmengen, die auf dem Plattenspeicher verwaltet werden.<br />

– Effiziente Algorithmen zum Sortieren großer Datenmengen<br />

� Effektive Anfragebearbeitung<br />

– Übersetzung und Optimierung von Anfragen<br />

– Anfrageoptimierung mit dem Ziel eines hohen Durchsatzes (Anfragen/Sekunde)<br />

Seite 13


Nach einer Umstrukturierung ...<br />

� Zugriff auf die Datenbank nur über ein DBMS<br />

� Es gibt nur einen zentralen Datenbestand<br />

– (eigentlichen) Daten<br />

– Metadaten (Daten über die Daten)<br />

– Funktionen<br />

Alfred Carlo Beatrice<br />

DBMS<br />

DB<br />

Einführung<br />

Seite 14


Datenabstraktion<br />

DBS besitzt mehrere Abstraktionsstufen:<br />

� Externe Ebenen: beschreiben den Teil der DB, der für<br />

einen Benutzer (oder eine Benutzergruppe) relevant ist.<br />

� Konzeptionelle Ebene gibt an, welche Daten und<br />

welche Beziehungen in der DB vorhanden sind<br />

� Physisches Ebene beschreibt, wie die Daten<br />

physisch abgelegt sind (physisches Datenmodell)<br />

Datenbankschema<br />

� Enwurf der Datebank bzgl. der drei Ebenen:<br />

– externe Schemata<br />

– ein konzeptionelle Schema<br />

– ein physisches Schema.<br />

� AWP greifen über ein externes Schema auf die Daten eines DBS zu.<br />

Datenbankzustand<br />

� Konkrete Instanz, die dem Datenbankschema folgt.<br />

AWP<br />

externe<br />

Ebenen<br />

konzeptionelle<br />

Ebene<br />

physische<br />

Ebene<br />

Einführung<br />

Seite 15


Datenunabhängigkeit<br />

Einführung<br />

� bezeichnet die Eigenschaft, das Schema in einer Ebene zu ändern, ohne dabei das Schema der<br />

Daten in der darüber liegenden Ebene zu beeinflussen.<br />

� Logische Datenunabhängigkeit:<br />

– Änderungen an der konzeptionellen Ebene haben keine<br />

Auswirkungen auf die externe Ebene und damit auch<br />

nicht auf die AWP.<br />

– Beispiel:<br />

Daten bei der Kont<strong>of</strong>ührung sollen um das Attribut<br />

“Uhrzeit” erweitert werden.<br />

� Physische Datenunabhängigkeit:<br />

– Änderungen an der physischen Ebene haben keine<br />

Auswirkungen auf die konzeptionelle Ebene und<br />

damit auch nicht auf die externe Ebenen und die AWP.<br />

– Beispiele:<br />

Der Datenbestand “Kont<strong>of</strong>ührung” soll statt in einer<br />

Datei auf mehrere Dateien verteilt gespeichert werden.<br />

AWP<br />

externe<br />

Ebenen<br />

konzeptionelle<br />

Ebene<br />

physische<br />

Ebene<br />

Der Algorithmus für das externe Sortieren wird neu implementiert.<br />

Ein Suchbaum soll aufgebaut werden, um schneller Anfragen zu beantworten.<br />

Seite 16


Datenmodelle<br />

� Ein Datenmodell ist ein Formalismus zur Beschreibung und Definition<br />

– von Daten<br />

– und von Operationen zur Datenmanipulation.<br />

Dies beinhaltet nicht nur die Syntax, sondern insbesondere auch die Semantik!<br />

� Typischerweise besitzt ein DBS zumindest zwei Datenmodelle:<br />

– physisches Datenmodell: zur speicher-orientierten Repräsentation der Daten<br />

– logisches Datenmodell: zur benutzer-orientierten Repräsentation der Daten<br />

� logische Datenmodelle sind<br />

– objekt-orientiert, z. B.<br />

Entity-Relationship Modell<br />

objektorientiertes Modell<br />

– satz-orientiert, z. B.<br />

relationales Datenmodell<br />

Netzwerk-Datenmodel<br />

hierarchisches Datenmodell<br />

Einführung<br />

Seite 17


Sprachen in DBS<br />

Datendefinitionssprache (DDL = data definition language)<br />

� Sprache zur Manipulation des Datenbankschemas<br />

� Verwaltung von Meta-Daten zur Beschreibung des Schemas (data dictionary)<br />

� Spezifikation von “lästigen” Implementierungsdetails<br />

Datenmanipulationssprache (DML = data manipulation language)<br />

Einführung<br />

� Funktionalität:<br />

– Einfügen, Löschen und Ändern von Datenobjekten in (aus) der Datenbank<br />

– Suche nach Datenobjekten in der Datenbank<br />

� Anfragesprachen sind i.a. deklarativ<br />

– Benutzer spezifiziert nur, was für Daten gesucht werden, aber nicht wie die Daten<br />

gefunden werden sollen.<br />

� Herausforderung<br />

– Anfrage, die ein Benutzer auf seiner externen Ebene deklarativ formuliert hat, wird in<br />

eine effiziente, imperative Anfrage übersetzt, die auf Objekte der physischen Ebene<br />

aufsetzt.<br />

Seite 18


naiver<br />

Benutzer<br />

Code des<br />

Anwenderprogramms<br />

Komponenten eines DBMS<br />

Anwendungsprogrammierer<br />

Precompiler<br />

der DML<br />

Dateisystem<br />

Dateien Dateien Daten-<br />

Dictionary<br />

Compiler<br />

der DML<br />

ad-hoc<br />

Anfrager<br />

Datenbank<br />

Manager<br />

Datenbankadministrator<br />

Compiler der<br />

Datendefinitionssprache<br />

Einführung<br />

Seite 19


Probleme heutiger Datenbanken<br />

� Neue Formen der Datenerfassung<br />

– Sensoren<br />

– Ticker<br />

– Anbindung von Web-Datenquellen<br />

� Dadurch ergeben sich sehr große und ständig wachsende Datenbanken<br />

– AT&T (2005)<br />

Größe<br />

• 330 TByte<br />

• 1,8 Billionen Elemente<br />

– UPS (2005)<br />

Systemlast (Maximum)<br />

• 315000 Anfragen/Sekunde<br />

– Steigerungsrate von 2003 bis 2005: Faktor 10<br />

� Zentrale Fragestellung<br />

– Wie kann man solche Datenmengen beherrschen?<br />

– Wie kann man DBMS bauen, die solch eine hohe Last unterstützen?<br />

Einführung<br />

Seite 20


Einführung<br />

Seite 21


Konzeptioneller Datenbankentwurf<br />

2. Konzeptioneller Datenbankentwurf<br />

Naive Vorgehensweise bei der Realisierung einer Datenbank<br />

� Informatiker definiert am Rechner das Datenbankschema<br />

Probleme<br />

� Datenbankschema ist hochgradig komplex<br />

– SAP-Datenbank besteht z. B. aus mehr als 20.000 Datentypen (ohne spezifische<br />

Benutzerdaten).<br />

==> Online-Entwicklung am Rechner ist nahezu unmöglich<br />

� Hohe Anzahl von Anwendungsprogrammen<br />

– Bei Unternehmen wie Allianz oder BMW greifen mehrere tausende AWP auf die gleiche<br />

Datenbank zu.<br />

==> Berücksichtigung der Bedürfnisse der Anwender ist zwingend erforderlich<br />

Seite 21


Datenorientierter Ansatz<br />

� Welche Daten müssen im System verwaltet werden?<br />

� Wie werden die Daten im System verändert?<br />

� Wie greifen die AWP auf die Daten zu?<br />

Datenbankentwurfsschritte<br />

Datenverarbeitungsanforderungen<br />

Anforderungsanalyse<br />

Informationsanforderungen<br />

Konzeptioneller<br />

Entwurf<br />

Logischer<br />

Entwurf<br />

DBMS-<br />

Eigenschaften<br />

Konzeptioneller Datenbankentwurf<br />

Hardware/BS-<br />

Eigenschaften<br />

Physischer<br />

Entwurf<br />

Seite 22


Anforderungsanalyse<br />

Konzeptioneller Datenbankentwurf<br />

� Diese Problemstellung wird primär im Bereich der S<strong>of</strong>twaretechnik betrachtet.<br />

– siehe auch die Veranstaltungen von Pr<strong>of</strong>. Hesse/Pr<strong>of</strong>. Täntzer<br />

� Die Analyse basiert auf dem Wissen über Informationsstrukturanforderungen, z. B.<br />

– Was sind meine Objekte und deren Attribute?<br />

– Wie sehen die Beziehungen zwischen den Objekten aus?<br />

– Wie viele Objekte werden in meiner Datenbank auftreten?<br />

und die Datenverarbeitungsanforderungen, z. B.<br />

– Was sind meine typischen Prozesse?<br />

– Reihenfolge und Priorität der Operationen<br />

� Zentrales Problem bei der Anforderungsanalyse:<br />

– Entwickler einer Datenbank muss diese Informationen erst von den Benutzern der<br />

Datenbank bekommen!<br />

– Es gibt kein Patentrezept für eine erfolgreiche Anforderungsanalyse.<br />

� Resultat der Anforderungsanalyse<br />

– Pflichtenheft, in dem möglichst genau festgehalten wird, was die Datenbank zu leisten<br />

hat.<br />

Seite 23


Ziel:<br />

Konzeptioneller Entwurf<br />

� Erstellung eines Modells unabhängig vom<br />

– konkreten DBMS<br />

– und eines konkreten Datenbankmodells<br />

Methode<br />

Konzeptioneller Datenbankentwurf<br />

� Datenbeschreibung in einer formalen Sprache auf Basis eines Modells hoher Abstraktion<br />

– Ein bekanntes konzeptionelles Datenmodell ist das Entity-Relationship Modell (ER-<br />

Modell)<br />

– Ein insbesondere für OO-Sprachen wichtiges Datenmodell ist Bestandteil der UML<br />

(Unified Model Language).<br />

� Daten in der Datenbank (Instanzen) werden nicht betrachtet, sondern nur deren Schemata.<br />

Problem<br />

� Automatische Transformation einer Anforderungsanalyse in einen konzeptionellen Entwurf<br />

– Anforderungsanalyse ist informell, konzeptionelles Modell ist relativ formal<br />

– Weglassen irrelevanter Strukturen (Abstraktion der realen Objekte)<br />

Seite 24


Ziel<br />

Logischer Entwurf<br />

Konzeptioneller Datenbankentwurf<br />

� Abbildung der Datenstrukturen des konzeptionellen Modells in Datenstrukturen des darunter<br />

liegenden logischen Datenmodells, d.h., in konkrete Strukturen der entsprechenden Datenbank<br />

(z. B. Relationen, XML-Hierarchie)<br />

– Möglichst kompakte Repräsentation Daten (Vermeidung von Redundanz)<br />

� Datenstrukturen des logischen Modells abstrahieren von der physischen Repräsentation.<br />

– Konkretes DBMS hat keinen Einfluss auf die Modellierung<br />

Physischer Entwurf<br />

� Physische Repräsentation der Datenstrukturen des logischen Entwurfs in Dateien<br />

– Aufteilung einer Datei auf verschiedene Plattenspeichersysteme (Lastbalancierung)<br />

� Anlegen von Hilfsstrukturen wie z. B. Indexe zur Unterstützung von Anfragen.<br />

– Zu viele Indexe: Updates der Datenbank werden zu teuer<br />

– Zu wenige Indexe: Anfragen werden nicht effizient unterstützt.<br />

Seite 25


Konzeptioneller Datenbankentwurf<br />

2.1 Entity-Relationship Datenmodell<br />

� Kurz ER-Modell (Peter P. Chen: The Entity-Relationship Model - Toward a Unified View <strong>of</strong><br />

Data. in Trans. on <strong>Database</strong> <strong>Systems</strong> 1(1): 9-36(1976))<br />

� Das ER-Modell hat eine große Relevanz in der Praxis, insbesondere für<br />

– den konzeptionellen Entwurf von Datenbanken<br />

� Vorgehensweise beim DB-Entwurf (siehe oben)<br />

– Zunächst Anforderungsanalyse und Entwurf des ER-Modells<br />

– Dann Logischer Entwurf, d. h. Umsetzung des ER Modells in ein Datenbankmodell<br />

� Ziel:<br />

Modellierung eines Ausschnittes der “realen Welt” durch Abstraktion, so dass gewisse<br />

Fragen über die “reale Welt” mit Hilfe des Modells beantwortet werden können.<br />

– “Reale Welt”:Zunächst nur wahrnehmbar über Sinnesorgane. Menschliche Sprache ist<br />

bereits erster Abstraktions- und Modellierungsschritt.<br />

ER-Modell beschreibt “reale Welt” durch<br />

� Entitäten (Entities) mit<br />

� Eigenschaften (Attributes) und<br />

� Beziehungen (Relationships) zueinander.<br />

Seite 26


Informelle Definitionen<br />

Entität (Entity)<br />

Konzeptioneller Datenbankentwurf<br />

� Eine Entität existiert in der realen, zu modellierenden Welt und unterscheidet sich von<br />

anderen Entitäten.<br />

– Beispiele: (ISBN 3-929821-31-1, Datenbanken), (Sommer, C++)<br />

� Ähnliche Entitäten werden zu einer Entitätsmenge (Entity Set) zusammengefaßt.<br />

– Menge aller Bücher, Menge aller Vorlesungen, Menge aller Pr<strong>of</strong>essoren<br />

Eine Entitätsmenge umfaßt alle zusammengehörigen Entitäten unabhängig von der derzeitigen<br />

Ausprägung in der Datenbank. Man spricht dann auch von einem Entitätstyp.<br />

– Ein Entitätstyp wird durch die zugehörigen Attribute und weiteren Nebenbedingungen<br />

beschrieben.<br />

� Ein Attribut eines Entitätstyps beschreibt eine charakteristische Eigenschaft<br />

– Jedes Buch besitzt eine ISBN-Nummer, einen Autor, …<br />

– Die Werte eines Attributes stammen aus Wertebereichen wie INTEGER, STRING, …<br />

z. B. ist die ISBN-Nummer eines Buches ein String aus Ziffern<br />

� Eine minimale Menge von Attributen, anhand deren Werte sich alle Entitäten eines<br />

Entitätstyps unterscheiden lassen, wird als Schlüsselkandidat bezeichnet.<br />

– z.B. identifiziert die ISBN-Nummer das Buch<br />

Seite 27


Beziehung (Relationship)<br />

Konzeptioneller Datenbankentwurf<br />

� Eine Beziehung repräsentiert Zusammenhänge zwischen Entitäten.<br />

Beispiele:<br />

– Student Maier hört Vorlesung DBS I<br />

– Es gibt ein Buchexemplar zum Buch mit ISBN-Nummer 3-929821-31-1<br />

� Eine „homogene“ Menge von Beziehungen wird zu einer Beziehungsmenge (Relationsship-<br />

Sets) zusammengefaßt.<br />

– z. B. die Beziehung Hört_Vorlesung<br />

Eine Beziehungsmenge wird auch als Beziehungstyp bezeichnet, der durch eine geordnete<br />

Liste von Entitätstypen Ei ,1 � i � n, und zusätzlichen Attributen beschrieben wird.<br />

– n ist der Grad der Beziehung<br />

– Beziehungstypen können auch Attribute besitzen.<br />

Beispiel: Hört_Vorlesung besitzt als Eigenschaft die Nummer des Hörsaals<br />

– Der Grad einer Beziehung ist i. A. 2, aber eine Beziehung mit höherem Grad ist möglich.<br />

� Ein Entitätstyp darf in einem Beziehungstyp mehrfach vorkommen.<br />

– Zur Unterscheidung ist es dann wichtig an die mehrfach in einer Beziehung<br />

vorkommenden Entitätstypen eine Rolle zu vergeben.<br />

Seite 28


Konzeptioneller Datenbankentwurf<br />

Funktionalität von Beziehungstypen<br />

1:1-Beziehungen (one-to-one relationships)<br />

� Falls für einen Beziehungstyp RE �<br />

1<br />

� E �<br />

2<br />

jede Entität aus E zu höchstens einer Entität aus<br />

� �<br />

1<br />

E<br />

2<br />

in Beziehung steht und umgekehrt.<br />

1:M-Beziehungen (one-to-many relationships)<br />

� Falls für einen zweistelligen Beziehungstyp RE �<br />

1<br />

� E �<br />

� 2�<br />

jede Entität aus E1 mit beliebig vielen<br />

(also mehreren oder auch keinen) Entitäten aus E2 , aber jede Entität aus E2 mit maximal einer<br />

Entität aus E1 in Beziehung steht.<br />

M:N-Beziehungen (many-to-many relationships)<br />

� Falls für einen binären Beziehungstyp RE �<br />

1<br />

� E �<br />

jede Entität aus E1 mit beliebig vielen (also<br />

� 2�<br />

mehreren oder auch keinen) Entitäten aus E2 in Beziehung stehen kann und umgekehrt.<br />

Seite 29


Beispiele<br />

Konzeptioneller Datenbankentwurf<br />

� 1:1-Beziehung: ABTEILUNG wird geleitet von ANGESTELLTER<br />

Annahme: Jede Abteilung hat genau einen Leiter und kein Angestellter leitet mehr als eine<br />

Abteilung.<br />

� 1:M-Beziehung ANGESTELLTER arbeitet in ABTEILUNG<br />

Annahme: jeder Angestellte arbeitet in genau einer Abteilung.<br />

� N:M-Beziehung ANGESTELLTER arbeitet im PROJEKT<br />

Einige Besonderheiten:<br />

� Vergabe von Rollen an die Entitätstypen, wenn diese in einem Beziehungstyp mehrfach<br />

vorkommen<br />

– Beispiel: VORGESETZTER(CHEF: ANGESTELLTER, MITARBEITER:<br />

ANGESTELLTER) wobei CHEF und MITARBEITER Rollen für den Entitätstyp<br />

ANGESTELLTER sind.<br />

� Ein weiterer Beziehungstyp ist die Spezialisierung, bekannt auch als IS-A-Beziehung<br />

– ANGSTELLTER besitzt Attribute ANGNR, NAME und GEHALT<br />

– ZUGFUEHRER und TECHNIKER sind auch ANGESTELLTER, besitzen aber noch<br />

weitere Attribute<br />

Seite 30


Alternative Notationen<br />

Konzeptioneller Datenbankentwurf<br />

� Unsere Notation bei einer 1:N-Beziehungen hält(Pr<strong>of</strong>essor, Vorlesung) sieht folgendermaßen<br />

aus:<br />

1<br />

N<br />

Pr<strong>of</strong>essor hält Vorlesung<br />

� In der Literatur findet man auch die funktionale Schreibweise hält: Vorlesung |--> Pr<strong>of</strong>essor.<br />

Pr<strong>of</strong>essor hält Vorlesung<br />

Stattdesssen wird auch die funktionale Beziehung dadurch charakterisiert, wie <strong>of</strong>t eine Entität<br />

in der Beziehung mit einer anderen Entität auftreten kann.<br />

� Einige kommerzielle Anbieter verwenden die sogennannte “Krähenfußnotation”<br />

Pr<strong>of</strong>essor hält Vorlesung<br />

Seite 31


min-max-Notation<br />

Konzeptioneller Datenbankentwurf<br />

� Im Gegensatz zu den rein syntaktischen Unterschieden funktionaler Beziehungen, ist die minmax-Notation<br />

tatsächlich eine semantisch angereicherte Notation für Beziehungen.<br />

Definition<br />

� An einer Kante einer Relation R(E 1 ,E 2 ) wird ein Intervall (min i ,max i ) i=1,2 notiert. Dabei gilt:<br />

– für alle e1 � E1 : min1 � �e2�e1�e2� � R�<br />

�max1<br />

– für alle e2 � E2 : min2 � �e1�e1�e2� � R�<br />

�max2<br />

� Wenn es keine obere Schranke gibt (oder diese unbekannt ist), wird dies durch ein “*”<br />

gekennzeichnet.<br />

Beispiel:<br />

(0,4) (1,1)<br />

Pr<strong>of</strong>essor hält Vorlesung<br />

1<br />

N<br />

Seite 32


Konzeptioneller Datenbankentwurf<br />

Beziehungen mit mehr als zwei Entitäten<br />

Funktionale Notation<br />

� Im Folgenden betrachten wir eine Relation RE � 1� …� Ek� mit k Entitäten. Wir ordnen in<br />

unserer Notation der Kante zur Entität eine “1” zu, falls<br />

eine Funktion ist. Ansonsten wird ein Symbol M,N,…zugeordnet.<br />

� Beispiel:<br />

E j<br />

R: �E1� …� Ej – 1�<br />

Ej + 1�<br />

…� Ek� � Ej 1<br />

N<br />

Pr<strong>of</strong>essor hält Vorlesung<br />

M<br />

Raum<br />

Seite 33


Konzeptioneller Datenbankentwurf<br />

Beziehungen mit mehr als zwei Entitäten<br />

min-max-Notation<br />

� Die min-max-Notation lässt sich auch verallgemeinern. Dabei betrachten wir k Intervalle<br />

�minj� maxj�, 1 � j� k,<br />

wobei folgende Bedingungen gelten:<br />

� Beispiel:<br />

minj minej � Ej Re1 … ej … e ( � � � � k)<br />

maxej � Ej Re1 … ej … e � � ( � � � � k)<br />

�maxj<br />

(0,8) (1,2)<br />

1<br />

N<br />

Pr<strong>of</strong>essor hält Vorlesung<br />

(0,*)<br />

M<br />

Raum<br />

Seite 34


2.1.1 ER-Diagramm<br />

Konzeptioneller Datenbankentwurf<br />

� Graphische Repräsentation von Entitätstypen, Beziehungstypen und ihrer Attribute<br />

Folgende Vereinbarungen werden getr<strong>of</strong>fen:<br />

� Ein Rechteck repräsentiert einen Entitätstyp:<br />

� Ellipsen repräsentieren Attribute:<br />

– Sie sind über ungerichtete Kanten mit ihrem Entitätstyp verbunden.<br />

– Schlüssel-Attribute werden unterstrichen.<br />

� Ein Beziehungstyp wird durch eine Raute repräsentiert:<br />

– Beziehungstypen werden mit ihren Entitätstypen durch Kanten verbunden.<br />

– Die Kanten werden mit der Funktionalität des in der Beziehung auftretenden Entitätstyps<br />

gekennzeichnet.<br />

a) Bei 1:1-Beziehungen besitzen beide Kanten das Symbol “1”.<br />

b) Bei N:1-Beziehungen zwischen E1 und E2 ist die Kante zu E1 mit dem Symbol<br />

“N” und die Kante zu E2 mit dem Symbol “1” gekennzeichnet.<br />

c) Bei N:M-Beziehungen wird “N” der einen und “M” der anderen Kante zugeordnet.<br />

Seite 35


Id-Beziehungen<br />

2.1.2 Erweiterungen<br />

Konzeptioneller Datenbankentwurf<br />

� Id-Beziehungen sind spezielle 1:N-Beziehungen, wobei die Existenz einer Entität von einer<br />

anderen Entität abhängt.<br />

– Man bezeichnet dann auch den existenzabhängigen Entitätstyp als schwach und den<br />

anderen Entitätstyp als stark.<br />

� Graphische Notation<br />

� Beispiel:<br />

schwache<br />

Entität<br />

Abteilung<br />

Id-Beziehung<br />

1 N<br />

Ang<br />

Seite 36


Konzeptioneller Datenbankentwurf<br />

IS-A-Beziehungen (Typerweiterung)<br />

� Eine Entität vererbt alle ihre Eigenschaften an eine andere Entität. Die Beziehung zwischen<br />

den Entitätstypen wird als IS-A-Beziehung bezeichnet.<br />

� IS-A-Beziehung wird für die Partitionierung einer Menge in (disjunkte) Teilmengen<br />

verwendet. Beide Entitätstypen einer IS-A-Beziehung besitzen den gleichen Schlüssel.<br />

� Beispiel<br />

– ANGSTELLTER besitzt Attribute ANGNR, NAME und GEHALT<br />

– Pr<strong>of</strong>essoren sind auch ANGESTELLTER, besitzen aber noch weitere Attribute wie z. B.<br />

FACHGEBIET<br />

Pr<strong>of</strong>essor<br />

Angestellter<br />

IS-A<br />

Mitarbeiter<br />

Besonderheit von IS-A und Id-Beziehungstypen<br />

� Es gibt höchstens einen IS-A oder Id-Beziehungstyp zwischen zwei Entitätstypen<br />

Seite 37


Konzeptioneller Datenbankentwurf<br />

2.2 Entwurf eines ER-Diagramms<br />

Anhand des Beispiels eines Auskunft- und Buchungssystem für das DB-ICE-Netz<br />

Mögliche Anfragen (Datenverarbeitungsanforderungen)<br />

� Wann fährt ein Zug von München nach Bremen?<br />

� Reserviere einen Platz von München nach Frankfurt im Zug ICE621 am 6.5.2009.<br />

� Gib Liste der reservierten Plätze in Zug ICE621 am 6.5.2006.<br />

� Gibt es eine Verbindung von München nach Essen mit Abfahrt zwischen 8.00 und 10.00 (ohne<br />

umzusteigen)?<br />

Informationsanforderungen:<br />

Entitätstypen:<br />

� Zug<br />

� Wagen<br />

� Platz<br />

� Bahnh<strong>of</strong><br />

Attribute:<br />

� Zugnr, Name, Verkehrstage<br />

� Wagennr., Klasse, Platzanzahl, R/NR<br />

� Platznr, Fenster<br />

� Name, Umsteigebahnh<strong>of</strong><br />

Seite 38


Beziehungstypen:<br />

� Zugplan: Zug x Wagen<br />

� Wagenplan: Wagen x Platz<br />

� Belegung: Platz x Bahnh<strong>of</strong> x Bahnh<strong>of</strong><br />

� Halt: Zug x Bahnh<strong>of</strong><br />

� Zuglauf: Zug x Bahnh<strong>of</strong> x Bahnh<strong>of</strong> x Bahnh<strong>of</strong><br />

� Verbindung: Bahnh<strong>of</strong> x Bahnh<strong>of</strong> x Bahnh<strong>of</strong><br />

Einschränkungen:<br />

� Keine Reservierungen eines Platzes auf überlappenden Teilstrecken<br />

� Übereinstimmung der Zeiten in den Beziehungstypen Halt und Verbindung<br />

Konzeptioneller Datenbankentwurf<br />

Seite 39


ER-Diagramm<br />

Konzeptioneller Datenbankentwurf<br />

Zug Zugplan Wagen Wagenp. Platz<br />

Halt<br />

Zuglauf<br />

Bahnh<strong>of</strong><br />

Verbind.<br />

Belegung<br />

Seite 40


Zusammenfassung<br />

Konzeptioneller Datenbankentwurf<br />

� Datenbankentwurf ist ein äußerst komplexer Vorgang!<br />

� ER-Modellierung ist ein auch in der Industrie anerkanntes und weit verbreitetes Verfahren zur<br />

Datenmodellierung<br />

– Voraussetzung ist eine detaillierte Anforderungsanalyse<br />

– ER-Modell unabhängig vom Typ der Datenbank und dem konkreten System<br />

� Wichtige Komponenten des ER-Modells<br />

– Entität und Entitätstyp<br />

– Attribut<br />

– Beziehung und Beziehungstyp<br />

� Charakterisierung von Beziehungstypen<br />

– N:M, 1:M, 1:1-Beziehungen<br />

– min-max-Notation<br />

– IS-A-Beziehung, Has-A-Beziehung<br />

– “starke” Beziehungen<br />

� Frage:<br />

Wie kann das ER-Modell in ein Modell eines spezifischen Datenbanktyps abgebildet werden?<br />

Seite 41


3. Das Relationale Datenmodell<br />

Das Relationale Datenmodell<br />

� Entwicklung des relationalen Modells durch Codd (1970):<br />

E. F. Codd: A Relational Model <strong>of</strong> Data for Large Shared Data Banks. Comm. <strong>of</strong> <strong>the</strong> ACM<br />

13(6): 377-387(1970)<br />

� Kommerzielle DBMS wie z. B.<br />

– Oracle, SQL Server, Sybase, Informix, DB2<br />

und nicht-kommerzielle Systeme wie z. B.<br />

– Firebird, mySQL, PostgreSQL, MaxDB, Derby<br />

basieren in ihren Grundzügen auf dem relationalen Datenmodell<br />

Gründe für den Erfolg des relationalen Datenmodells<br />

� Einfachheit<br />

– Relation (vergleichbar mit einer Tabelle) als wesentliche Datenstruktur<br />

� Wenige, aber ausdrucksstarke Grundoperationen zur Verarbeitung<br />

– klare Semantik<br />

� Mengenorientierte Verarbeitung der Daten<br />

� Formale Fundierung der Modellierung und der Anfrageverarbeitung<br />

Seite 43


3.1 Grundlegende Strukturen<br />

Definition: Eine Relation R besteht aus folgenden Komponenten:<br />

Das Relationale Datenmodell<br />

1. einem Namen<br />

2. ein Relationenschema <strong>RS</strong>R – Ein Relationenschema definiert die spezifische Struktur der Relation. <strong>RS</strong>R wird durch<br />

eine Liste von k Attributen (A1 ,…,Ak ) beschrieben, wobei es zu jedem Attribut Aj einen<br />

Wertebereich Dj = dom(Aj ) gibt. Der Wertebereich der Relation ist dann<br />

dom( R)<br />

= D<br />

1<br />

� D<br />

2<br />

��D k<br />

, k � 1<br />

– Der Wertebereich eines Attributs ist endlich und besteht aus atomaren Elementen, die<br />

keine weitere Struktur besitzen. Beispiele hierfür sind int oder String.<br />

Oft sind weitere semantische Eigenschaften bekannt, welche zu einer erheblichen<br />

Verkleinerung des Wertebereichs führen können.<br />

3. eine Instanz IR Darunter verstehen wir eine Teilmenge des Wertebereichs:<br />

I<br />

R<br />

�<br />

dom( R)<br />

Ein Tupel (Zeile, Datensatz) der Relation R entspricht einem Element der Relationeninstanz<br />

I R . Ein Tupel hat somit für jedes Attribut genau einen Wert.<br />

Seite 44


Notation<br />

Das Relationale Datenmodell<br />

� Tupel: (Franz, 2000, 1966)<br />

Dies könnte ein Tupel einer Relation Personal mit den Attributen Name, Gehalt und<br />

Geburtsjahr sein.<br />

� Relationenschema einer Relation R: <strong>RS</strong>R = (A1 ,…,Ak )<br />

– Für eine Relation R mit k Attributen bezeichnet k die Grad (Stelligkeit) von R.<br />

– In der Literatur findet man auch häufig die Schreibweise R(A1 ,…,Ak ).<br />

� Relationeninstanz einer Relation R: I R = {t 1 ,…,t n }, wobei t i die Tupel sind.<br />

Vereinfachte Notation und weitere Begriffe<br />

� Der Begriff Relation wird <strong>of</strong>t auch für die Instanz einer Relation verwendet.<br />

� Ist klar, um welche Relation es sich handelt, wird der Index bei der Instanz und beim Schema<br />

einfach weggelassen.<br />

� Häufig wird eine Relation als Tabelle dargestellt:<br />

Pers1 Name Gehalt GebJahr<br />

Carlo 2000 1981<br />

Beate 3000 1977<br />

Pers 1 ist der Relationennamen. Name, Gehalt, GebJahr sind die Attributsnamen.<br />

Seite 45


Gleichheit von Relationen<br />

� Seien R und S zwei Relationen. Dann sind R und S schemakonform, falls<br />

– dom(R) = dom(S)<br />

– und <strong>RS</strong>R = <strong>RS</strong>S .<br />

Das Relationale Datenmodell<br />

� Zwei Relationen R und S sind gleich, wenn R und S schemakonform sind und I R = I S .<br />

Bemerkungen<br />

� Relationen sind vergleichbar mit Variablen aus imperativen Programmiersprachen. Relationen<br />

sind Speicherbereiche in der Datenbank, die über den Relationennamen angesprochen werden<br />

können.<br />

Seite 46


Reihenfolge der Attribute<br />

Das Relationale Datenmodell<br />

� Bei unserer bisherigen Definition einer Relation hat die Reihenfolge der Zeilen (Tupel) keine<br />

Bedeutung. Eine Instanz wird immer als eine Menge von Tupel betrachtet.<br />

� Die Reihenfolge der Attribute ist aber von Bedeutung, was insbesondere dazu führt:<br />

Pers1 Name Gehalt GebJahr<br />

Carlo 2000 1981<br />

Beate 3000 1977<br />

� Um die Gleichheit solcher Relationen zu erzielen, betrachten wir folgende Definition für eine<br />

Relation R:<br />

– Das Schema <strong>RS</strong>R von R besteht aus einer Menge von Attributen: <strong>RS</strong>R Jedes Attribut verfügt wie bisher über einen Wertebereich.<br />

= �A1� …� Ak�. – Die zu R gehörende Instanz IR ist eine endliche Menge von totalen Abbildungen der<br />

k<br />

�<br />

Form t: <strong>RS</strong>R � dom( Ai) , wobei tA ( j)<br />

�<br />

dom( Aj) gilt.<br />

i = 1<br />

=<br />

Pers2 Gehalt Name GebJahr<br />

2000 Carlo 1981<br />

3000 Beate 1977<br />

� Diese Definition liefert uns den gewünschten Effekt! Je nach Sachverhalt werden wir auf die<br />

eine oder die andere Definition zurückgreifen (siehe auch Literatur).<br />

Seite 47


Beispiel:<br />

Pers1 Name Gehalt GebJahr<br />

Carlo 2000 1981<br />

Beate 3000 1977<br />

� Relationenschema der Relation Städte:<br />

{Name, Gehalt, GebJahr} mit dom(Name) = String[40], dom(Gehalt) =<br />

Integer und dom(GebJahr) = Integer<br />

� Tupel t1 und t2 mit<br />

t 1 (Name) = Carlo, t 1 (Gehalt) = 2000 und t 1 (GebJahr) = 1981<br />

t 2 (Name) = Beate, t 2 (Gehalt) = 3000 und t 2 (GebJahr) = 1977<br />

Das Relationale Datenmodell<br />

Seite 48


Datenbank<br />

Das Relationale Datenmodell<br />

� Analog zu einer Relation wird eine Datenbank durch drei Eigenschaften beschrieben:<br />

– Name<br />

– Datenbankschema: Menge der Relationenschemata<br />

– Datenbankinstanz: Menge der Instanzen der Relationen<br />

� Viele der somit beschreibbaren Datenbankinstanzen können nicht auftreten. Es ist deshalb<br />

sinnvoll, die möglichen Datenbankinstanzen durch semantische Bedingungen einzuschränken.<br />

Seite 49


Einfache Integritätsbedingungen<br />

Das Relationale Datenmodell<br />

� Integritätsbedingungen sind semantische Eigenschaften einer Relation, welche die Menge der<br />

möglichen Instanzen einschränken. Im Folgenden werden wir eine wichtige Bedingung<br />

erläutern. Eine ausführliche Diskussion folgt später.<br />

Notation<br />

� Sei R eine Relation und <strong>RS</strong> das zugehörige Schema. Sei X�<strong>RS</strong>. Dann bezeichnet t[X] das<br />

Tupel t eingeschränkt auf X. Ist X = {A}, so schreiben wir kurz t[A] (statt t[{A}].<br />

Schlüssel<br />

� X�<strong>RS</strong> wird als Schlüssel bezeichnet, wenn folgende Bedingungen erfüllt sind:<br />

– Eindeutigkeit: Für alle (real möglichen) Relationeninstanzen I der Relation R gilt: Für<br />

zwei beliebige Tupel t1 und t2 aus I gilt:<br />

t<br />

1<br />

�X� = t<br />

2<br />

�X��t 1<br />

= t<br />

2<br />

– Minimalität: es gibt kein Y � X ( Y �<br />

X),<br />

so dass die Eindeutigkeit erfüllt ist.<br />

� Wenn mehrere Teilmengen eines Relationenschemas Schlüssel sind, wird einer von diesen als<br />

Primärschlüssel ausgezeichnet.<br />

– Die Attribute des Primärschlüssels werden im Schema unterstrichen.<br />

Seite 50


Das Relationale Datenmodell<br />

3.2 Abbildung eines ER-Schemas in ein<br />

� Datenstruktur der ER-Datenmodellierung<br />

– Entitätstypen<br />

– Beziehungstypen<br />

� Datenstruktur des relationalen Modells<br />

– Relationen (bzw. Relationenschema)<br />

Fragestellung<br />

relationales Schema<br />

� Wie kann ein ER Datenmodell in ein relationales Model umgesetzt werden?<br />

� Diese Frage wird nun in zwei Schritten beantwortet:<br />

– Einfache Umsetzung von Entitätstypen und Beziehungstypen<br />

– Konsolidierung des Relationenschemas<br />

Seite 51


Umsetzung eines Entitätstyps<br />

Das Relationale Datenmodell<br />

� Der Entitätstyp wird als eigenständige Relation umgesetzt, wobei jede Eigenschaft des<br />

Entitätstyps durch ein Attribut in der Relation dargestellt wird.<br />

� Die Namen der Attribute können entsprechend den Namen der Eigenschaften des Entitätstyps<br />

gewählt werden.<br />

� Der Schlüssel des Entitätstyps wird als Primärschlüssel des Relationenschemas vereinbart.<br />

� Beispiel (siehe ER Diagramm aus Kapitel 2):<br />

– Entität Zug:<br />

{ZugNr: Integer, Typ: String}<br />

– Entität Bahnh<strong>of</strong><br />

{Id: Integer, Stadt: String, Name: String}<br />

Seite 52


Umsetzung eines Beziehungstyps<br />

Das Relationale Datenmodell<br />

� Der Beziehungstyp wird als eigenständige Relation umgesetzt, wobei<br />

– die Primärschlüssel der beteiligten Entitäten vollständig im Relationenschema<br />

aufgenommen werden<br />

– und jedes Attribut des Beziehungstyps durch ein Attribut in der Relation dargestellt wird.<br />

� Die aus einem Primärschlüssel gewonnen Attribute werden als Fremdschlüssel bezeichnet.<br />

� Die Namen der Attribute eines Fremdschlüssels müssen z. T. umbenannt werden, damit eine<br />

Eindeutigkeit der Namen gewährleistet wird.<br />

� Beispiel (M:N-Beziehungstyp)<br />

– Umsetzung des M:N-Beziehungstyps hält und die am Beziehungstyp beteiligten<br />

Entitätstypen Zug und Bahnh<strong>of</strong>.<br />

– Der Schlüssel von hält entspricht dabei der Menge von Fremdschlüsseln.<br />

Zug Id Typ<br />

529 ICE<br />

621 ICE<br />

… …<br />

hält Zug Bhf Gleis<br />

529 1 7<br />

529 2 4a/b<br />

621 1 7<br />

621 3 22<br />

… … …<br />

Bahnh<strong>of</strong> Id Stadt Name<br />

1 Frankfurt Lahn<br />

2 Würzburg Hbf<br />

3 München Hbf<br />

… …<br />

Seite 53


Das Relationale Datenmodell<br />

� Beispiel (Umsetzung eines 1:N-Beziehungstyps)<br />

– Betrachten wir hierzu ein Beispiel aus der Universitätswelt, in der ein Pr<strong>of</strong>essor<br />

Vorlesungen abhält. Wenn der Primärschlüssel von Pr<strong>of</strong>essor die PersNr und die von<br />

Vorlesung die VorNr ist, würden die Beziehung liest als zweistellige Relation umgesetzt<br />

werden.<br />

– Man beachte aber, dass {PersNr, VorNr} kein Schlüssel von liest ist, da die Eigenschaft<br />

der Minimalität verletzt ist. {VorNr} erfüllt aber die Eigenschaft eines Schlüssels.<br />

� Mit der Fremdschlüsseleigenschaft bezeichnet man nun folgende Integritätsbedingung:<br />

– Sei F der Fremdschlüssel in R, der sich auf eine Relation S bezieht, so muss stets<br />

erfüllt sein.<br />

1 N<br />

Pr<strong>of</strong>essor liest Vorlesung<br />

IR�F� �<br />

IS�F� Seite 54


Konsolidierung des Schemas<br />

Das Relationale Datenmodell<br />

� Mögliche Vereinfachungen des Schemas durch Verschmelzen von Relationen, die aus einem<br />

zweistelligen Beziehungstyp der Kardinalität 1:1 oder 1:N hervorgegangen sind.<br />

� Seien R und S die Relationen der beteiligten Entitätstypen eines 1:N-Beziehungstyps und T die<br />

Relation des Beziehungstyps. Dann können wir alternativ folgendes Schema verwenden:<br />

– Statt der Relation S und T wird eine neue Relation U eingeführt, wobei<br />

<strong>RS</strong>U = <strong>RS</strong>S � <strong>RS</strong>T Die Instanzen von U sollen nun die gleiche Information wie zuvor die Instanzen von S<br />

und T enthalten. Hierzu verknüpfen wir die Tupel aus S und T bzgl. ihrer Fremdschlüssel.<br />

– Für die Tupel s � IS, die kein t � ITmit s[F] = t[F] besitzen, wird ein Tupel u erzeugt,<br />

so dass � � =<br />

s.<br />

u<strong>RS</strong> S<br />

– Die anderen Werte von u werden mit einem speziellen Wert (NULL) aufgefüllt.<br />

NULL-Werte signalisieren, dass der Wert bisher unbekannt ist. NULL-Werte sind bei<br />

einem Schlüssel explizit verboten.<br />

– Die Relation R bleibt unverändert bestehen.<br />

� Was sind die Vor- und Nachteile einer solchen Konsolidierung?<br />

Seite 55


Das Relationale Datenmodell<br />

Umsetzung von IS-A-Beziehungstypen<br />

� IS-A-Beziehungstypen werden nicht durch eine eigene Relation repräsentiert. Die Beziehung<br />

wird dadurch bereits ausgedrückt, wenn der Schlüssel des allgemeinen Typs auch als Schlüssel<br />

der spezialisierten Typen benutzt wird.<br />

� Beispiel:<br />

Pr<strong>of</strong>essor<br />

Angestellter<br />

IS-A<br />

Mitarbeiter<br />

ANGNR<br />

Name<br />

Fachgebiet Thema<br />

Daraus ergeben sich drei Relationen mit dem Schema {ANGNR, Name}, {ANGNR,<br />

Fachgebiet} und {ANGNR, Thema}.<br />

� Als Alternative bietet sich an, den IS-A-Beziehungstyp und die beteiligten Entitätstypen durch<br />

eine Relation mit Schema {ANGNR, Name, Fachgebiet, Thema} zu präsentieren und bei den<br />

Instanzen die fehlende Information durch NULL-Werte aufzufüllen.<br />

Was ist bei diesem Ansatz problematisch?<br />

Seite 56


mnr<br />

MName<br />

Beispiel (ER-Diagramm)<br />

Fähigkeit<br />

M PM- N<br />

Machinen Zuteilung Personal<br />

AName<br />

abtnr<br />

pnr<br />

N<br />

arbeitet_in<br />

1<br />

Abteilung<br />

PName<br />

1<br />

N<br />

Das Relationale Datenmodell<br />

leitet<br />

Seite 57


Datenbankschema:<br />

PM-Zuteilung:<br />

pnr mnr Fähigkeit<br />

67 84 3<br />

67 93 2<br />

67 101 3<br />

73 84 5<br />

114 93 5<br />

114 101 3<br />

51 93 2<br />

69 101 2<br />

333 84 3<br />

701 84 2<br />

701 101 2<br />

82 101 2<br />

Beispiel (Relationen)<br />

Abteilungsleiter:<br />

abtnr pnr<br />

B10 67<br />

A63 333<br />

A64 333<br />

Abteilung:<br />

abtnr AName<br />

B10 Spielzeug<br />

A63 Computer<br />

A64 Suppen<br />

Personal:<br />

mnr MName<br />

84 Presse<br />

93 Füllanlage<br />

101 Säge<br />

Das Relationale Datenmodell<br />

pnr PName Vorname Abt Lohn<br />

67 Meier Helmut B10 L4<br />

73 Müller Margot B10 L5<br />

114 Bayer Martin A63 L6<br />

51 Daum Birgit A64 L7<br />

69 Störmer Willi A64 L6<br />

333 Haar Hans A63 L6<br />

701 Reiner Willi A64 L6<br />

82 Just Michael A64 L6<br />

Maschinen:<br />

Seite 58


Was ist eine Algebra:<br />

3.3 Die relationale Algebra<br />

� Gegeben eine Menge N (“Anker der Algebra”)<br />

� Menge von Operationen { �<br />

1<br />

, …,<br />

�<br />

n<br />

} der Form �<br />

j<br />

: Nk �<br />

N<br />

Relationale Algebra<br />

� Anker ist die Menge aller Relationen<br />

� Menge von 6 Grundoperationen<br />

Das Relationale Datenmodell<br />

Seite 59


Das Relationale Datenmodell<br />

3.3.1 Grundoperationen der relationalen<br />

Algebra<br />

� Gegeben zwei Relationen R({A 1 ,…,A r }) und S({B 1 ,…,B s }) vom Grad r und s.<br />

– Zur Erleichterung der Definition sei hier angenommen, dass die Attribute der Relationen<br />

ungeordnet und die Tupel also Abbildungen sind. Dann gilt:<br />

IR � �t | �tA � i�<br />

� dom�Ai��1� i� r��<br />

und IS � �t | �tB � i�<br />

� dom�Bi��1�i �s��<br />

� Vereinigung: R � S<br />

– Voraussetzung: R und S sind schemakonform.<br />

– <strong>RS</strong>R � S = <strong>RS</strong>R und IR � S = IR � IS � Differenz: R– S<br />

– Voraussetzung: R und S sind schemakonform.<br />

– <strong>RS</strong>R – S = <strong>RS</strong>R und IR – S = IR \ IS � Kartesisches Produkt: R�S – Voraussetzung: <strong>RS</strong>R �<strong>RS</strong>S = �<br />

– <strong>RS</strong>R � S = <strong>RS</strong>R � <strong>RS</strong>S und IR S<br />

=<br />

�<br />

� I R I S<br />

Seite 60


� Projektion: Sei X � <strong>RS</strong>R, X � �.<br />

Dann ist<br />

<strong>RS</strong>�X�R� X<br />

= und I<br />

�X�R� Das Relationale Datenmodell<br />

Statt der Angabe einer Teilmenge X = {A,B,C,…} werden üblicherweise bei der Projektion<br />

nur die Attribute A,B,C,… als Index der Projektion verwendet. Z. B.:<br />

�A� B� C�R�<br />

= � A� B� C<br />

� Selektion:<br />

Dabei ist F eine Boolesche Funktion (Prädikat), die sich folgendermaßen zusammensetzt:<br />

a) Operanden: Konstanten oder Name eines Attributs<br />

b) Vergleichsoperatoren: = , � , � , � , � ,�<br />

c) Boolesche Operatoren: � , � , �<br />

–<br />

–<br />

�F�R� � �<br />

� � R<br />

<strong>RS</strong>�F�R� = <strong>RS</strong>R I �F R<br />

=<br />

� � t | t I R<br />

=<br />

� � � Ft () �<br />

�r �t<br />

� IR : r = t�X�� � Umbenennen von Relationen und Attributen (“+ 1- Operation”)<br />

�S�R�: Relation R wird in Relation S umbenannt<br />

Seite 61


�B � A R<br />

� �:<br />

Attribut A der Relation R wird umbenannt in B<br />

Das Relationale Datenmodell<br />

– Umbenennung unterscheidet sich von den anderen Operatoren dadurch, dass keine neue<br />

Instanz erzeugt wird, sondern nur das Schema der Relation verändert wird.<br />

– Operator ist notwendig für binäre Operatoren, wenn beispielsweise<br />

a) eine Relation mehrfach im Kreuzprodukt vorkommt,<br />

b) zwei Relationen bei der Vereinigung nicht schemakonform sind.<br />

– Werden gleichzeitig A1 in B1 , A2 in B2 , …, Ak in Bk umbenannt, benutzen wir die<br />

verkürzte Schreibweise: �R�. �B1� �� Bk � A1���Ak Seite 62


Beispiele (abstrakt)<br />

R A B C<br />

a b c<br />

d a f<br />

c b d<br />

R�T �A�C a b c<br />

d a f<br />

c b d<br />

b g a<br />

S D E F<br />

b g a<br />

d a f<br />

R– T<br />

a b c<br />

c b d<br />

�R� A C<br />

A B C<br />

� �<br />

a c<br />

d f<br />

c d<br />

�B = b R<br />

a b c<br />

c b d<br />

T = �A B C<br />

T A B C<br />

b g a<br />

d a f<br />

� � � D�E�F R�S �S� Das Relationale Datenmodell<br />

A B C D E F<br />

a b c b g a<br />

a b c d a f<br />

d a f b g a<br />

d a f d a f<br />

c b d b g a<br />

c b d d a f<br />

Seite 63


� Relationenschemata: siehe Seite 58<br />

Beispiele für Anfragen<br />

Das Relationale Datenmodell<br />

� Bestimme alle Personen und deren Lohngruppe, die in Lohngruppe L5 oder höher sind.<br />

�PName� Lohn �Lohn � ’’L5’’<br />

� �Personal�� � In welcher Abteilung arbeitet Müller?<br />

�abtnr��PName = ’’Müller’’ �Personal�� � Bestimme die Personen mit gleichem Vornamen.<br />

�PersNr� pnr��VN<br />

= Vorname�Personal<br />

� �PersNr � pnr�<br />

VN � Vorname��Vorname�<br />

pnr�Personal����<br />

� Finde die Namen aller Personen aus der Abteilung Computer.<br />

�PName��Abt = abtnr�Personal<br />

� �AName = ’’Computer’’ �Abteilung��� � Finde alle Personen, die nur an der Maschine mit Nummer 84 ausgebildet sind.<br />

�pnr��mnr = 84�PM-Zuteilung��–<br />

�pnr��mnr � 84�PM-Zuteilung��<br />

Seite 64


Durchschnitt:<br />

� R�S = R – �R– S�<br />

� Beispiel:<br />

3.3.2 Abgeleitete Operationen<br />

R�S R B C D<br />

b c a<br />

b c d<br />

b f b<br />

a d c<br />

S B C D<br />

b c d<br />

b c e<br />

a d b<br />

R�S Das Relationale Datenmodell<br />

B C D<br />

b c d<br />

Seite 65


Quotient (Division):<br />

� vereinfachende Annahme:<br />

� und IS � �<br />

<strong>RS</strong> R<br />

� Relationenschema des Quotienten:<br />

<strong>RS</strong>R S = –<br />

� Resultatsinstanz des Quotienten:<br />

� Beispiel:<br />

<strong>RS</strong> S<br />

I R S<br />

R�S � <strong>RS</strong> R <strong>RS</strong> S<br />

� = �t � s � IS�u�IR: u�<strong>RS</strong>S� = s � u<strong>RS</strong> � R – <strong>RS</strong>S� = t�<br />

R A B C D<br />

a b c d<br />

a b e f<br />

b c e f<br />

e d c d<br />

e d e f<br />

a b d e<br />

S C D<br />

c d<br />

e f<br />

R�S A B<br />

a b<br />

e d<br />

Das Relationale Datenmodell<br />

Seite 66


Natürlicher Verbund (natural join):<br />

Das Relationale Datenmodell<br />

� Der natürliche Verbund ist die wichtigste Operation neben der Selektion. Er stellt eine echte<br />

Verallgemeinerung des kartesischen Produkt dar.<br />

– Der Unterschied zum kartesischen Produkt tritt dann auf, wenn der Schnitt der beiden<br />

Schemata nicht leer ist, d. h. � � �.<br />

� Dann ist<br />

� Beispiel:<br />

<strong>RS</strong> R S<br />

=<br />

<strong>RS</strong> R<br />

�<br />

<strong>RS</strong> S<br />

<strong>RS</strong> R<br />

<strong>RS</strong> S<br />

R S<br />

I<br />

R S<br />

= �t | � s�Is: t�<strong>RS</strong>S� = s � � r�Ir: t�<strong>RS</strong>R� = r�<br />

R B C A<br />

b c a<br />

b c d<br />

b f b<br />

a d c<br />

S B C D<br />

b c d<br />

b c e<br />

b d a<br />

a d b<br />

R S<br />

B C A D<br />

b c a d<br />

b c a e<br />

b c d d<br />

b c d e<br />

a d c b<br />

Seite 67


Theta-Join (Verbund):<br />

Das Relationale Datenmodell<br />

� Auswahl bestimmter Tupel aus dem kartesischen Produkt R�S: – Voraussetzung: A�<strong>RS</strong>R, B � <strong>RS</strong>S, <strong>RS</strong>R �<strong>RS</strong>S = � und � � { = , � , � , � , � , � }<br />

–<br />

RA�BS := �A � B�R�S� R A�B S<br />

� Für � = “=“ wird der Join auch als Equi-Join bezeichnet.<br />

� Beispiel:<br />

R A B C<br />

1 2 3<br />

4 5 6<br />

7 8 9<br />

S D E<br />

3 1<br />

6 2<br />

RB � DS<br />

A B C D E<br />

1 2 3 3 1<br />

1 2 3 6 2<br />

4 5 6 6 2<br />

Seite 68


Anfragen<br />

� Finde alle Namen von Personen, die an einer Maschine ausgebildet sind.<br />

�<br />

PName<br />

�Personal PM-Zuteilung�<br />

Das Relationale Datenmodell<br />

� Finde alle Namen der Personen, die an keiner Maschine genügend gut ausgebildet sind.<br />

�<br />

PName<br />

��� pnr<br />

�Personal� – �<br />

pnr<br />

�� Fähigkeit � 5<br />

�PM-Zuteilung��� Personal�<br />

� Finde die Namen der Personen aus Abteilung “Suppen”, die an der Maschine mit mnr = 93<br />

ausgebildet sind.<br />

�<br />

PName<br />

���� AName = Suppen<br />

�Abteilung�� Personal�<br />

�<br />

mnr = 93<br />

�PM-Zuteilung�� � Finde die Namen der Personen, die an der gleichen Maschine ausgebildet sind wie die Person<br />

mit pnr = 114.<br />

�<br />

PName<br />

�Personal ��� mnr<br />

�� pnr = 114<br />

�PM-Zuteilung��� PM-Zuteilung��<br />

Seite 69


Weitere Join-Operatoren<br />

� Bisherige Join-Operatoren werden auch als innere Joins bezeichnet.<br />

Äußere Join-Operatoren (engl.: outer joins):<br />

Das Relationale Datenmodell<br />

� Problem von inneren Joins: Datensätze ohne Join-Partner gehen verloren.<br />

– Beim äußeren Join bleiben Datensätze ohne Join-Partner (teilweise) erhalten. Die nicht<br />

bekannten Attribute werden mit Nullwerten aufgefüllt.<br />

� Schema des äußeren Joins entspricht dem des inneren Joins<br />

� Varianten<br />

– linker äußerer Join R S: Tupel von R bleiben erhalten<br />

– rechter äußerer Join R S: Tupel von S bleiben erhalten<br />

– vollständiger äußerer Join R S: Tupel von S und R bleiben erhalten<br />

� Beispiel<br />

R A B C<br />

a 1 b 1 c 1<br />

a 2 b 2 c 2<br />

S C D E<br />

c 1 d 1 e 1<br />

c 3 d 2 e 2<br />

R S A B C D E<br />

a 1 b 1 c 1 d 1 e 1<br />

a 2 b 2 c 2 NULL NULL<br />

Seite 70


Semi-Join<br />

� Der Semi-Join von R und S ist folgendermaßen definiert:<br />

R S = � �R S�<br />

<strong>RS</strong>R<br />

Das Relationale Datenmodell<br />

– Der Semi-Join berechnet also alle Tupel der Relation R, die am Join mit der Relation S<br />

beteiligt sind.<br />

� Beispiel<br />

R A B C<br />

a 1 b 1 c 1<br />

a 2 b 2 c 2<br />

S C D E<br />

c 1 d 1 e 1<br />

c 3 d 2 e 2<br />

R S A B C<br />

a 1 b 1 c 1<br />

Seite 71


Bisher:<br />

3.4 Das Relationenkalkül<br />

� Benutzung einer prozeduralen Anfragesprache<br />

� Explizite Beschreibung, wie das Ergebnis berechnet wird<br />

Zugrunde liegende Idee beim Relationenkalkül:<br />

Das Relationale Datenmodell<br />

� Ergebnis einer Anfrage ist eine Menge von Tupel<br />

� Beschreibung der Ergebnisrelation ohne dabei explizit eine Vorschrift für die<br />

Konstruktion des Ergebnisses anzugeben.<br />

� Prädikatenlogik erster Stufe<br />

Zwei verschiedene Techniken<br />

� Tupelkalkül<br />

� Domänenkalkül<br />

Seite 72


3.4.1 Das Tupelkalkül<br />

� Eine Anfrage im Tupelkalkül wird wie folgt formuliert:<br />

Das Relationale Datenmodell<br />

– f ist hierbei eine Boolesche Funktion.<br />

– Die Ergebnismenge der Anfrage ist durch die Tupel t aus dem Schema <strong>RS</strong><br />

gegeben mit ft ��= true.<br />

– Wird kein Schema explizit angegeben, ergibt sich das Schema implizit aus dem<br />

minimal notwendigen Schema für die Formel f .<br />

– Häufig ergibt sich das Schema aus der verbalen Formulierung der Anfrage. Das<br />

Schema wird deshalb bei den Formeln nicht immer explizit angegeben.<br />

Beispiele:<br />

�t<strong>RS</strong> � � | ft ���<br />

� Was sind die Namen der Mitarbeiter aus Abteilung A63?<br />

�t�PName� | �s � Personal mit t[PName] = s[PName] und s[abtnr] = “A63“ �<br />

� Quotient der Relationen R mit Schema <strong>RS</strong>R und S mit Schema <strong>RS</strong>S , � :<br />

�t<strong>RS</strong> � R – <strong>RS</strong>S� | �ts � S �tr � R mit tr�<strong>RS</strong>R – <strong>RS</strong>S� = t und tr�<strong>RS</strong>S� = ts� <strong>RS</strong> S<br />

<strong>RS</strong> R<br />

Seite 73


Formeln des Tupelkalküls<br />

� Eine Formel f setzt sich zusammen aus Atomen der Form<br />

– R(s): s ist Element der Relation R (s ist Tupelvariable)<br />

– s[i] � u[j] mit � � � = , � , � , � , � ,��<br />

– s[i] � a<br />

–<br />

Beispiele:<br />

� Personal(t), t[Fähigkeit] > 4, t[abtnr] = u[abtnr]<br />

Eine Formel ist entweder durch<br />

� ein Atom<br />

oder rekursiv durch folgende Ausdrücke definiert (Ann.: f und g sind Formeln):<br />

� f�g, f�g, �f, �� f<br />

� �s<strong>RS</strong> � �f,<br />

�s<strong>RS</strong><br />

� �f<br />

Das Relationale Datenmodell<br />

– s ist eine Tupelvariable in f<br />

und <strong>RS</strong> ist das zur Variablen s gehörende Schema<br />

Seite 74


Bemerkung:<br />

� Reihenfolge der Ausführung: � und �;<br />

�;<br />

� ; �<br />

� Klammern setzten die Reihenfolge außer Kraft<br />

Beispiele:<br />

Annahme: Tupelvariable x ist aus dem Schema {pnr,mnr,Fähigkeit}<br />

� �x�Fähigkeit��4 �<br />

�<br />

�<br />

�x�pnr� = ypnr � ��<br />

� �x�Fähigkeit� � 4<br />

PM-Zuteilung�x���xpnr � � = ypnr � ��<br />

� �x�Fähigkeit� � 4<br />

�x�PM-Zuteilung�x�<br />

� �xpnr � � = y�pnr�� � �x�Fähigkeit� � 4�<br />

Das Relationale Datenmodell<br />

Seite 75


Das Relationale Datenmodell<br />

Freie und gebundene Tupelvariablen<br />

� Freie und gebundene Variablen im Tupelkalkül entsprechen globalen und lokalen<br />

Variablen in einem Programm.<br />

� Durch Angabe eines Quantors direkt vor einer freien Variablen wird diese gebunden.<br />

Definition<br />

– Das Auftreten einer Tupelvariablen in einem Atom ist stets frei.<br />

– Für f = �g<br />

und f = �g� sind alle freien Variablen von g auch frei in f.<br />

– Für f = g�h und f = g�h sind die Variablen in f frei, falls sie es in g und h sind.<br />

– Sei x eine freie Variable in g. Dann wird durch f = �x �<strong>RS</strong>��g� und f = �x (<strong>RS</strong>) �g� x zu einer gebundenen Variable in f. Dabei ist <strong>RS</strong> das Schema der Variable x.<br />

Beispiel:<br />

�x��pnr�mnr�Fähigkeit����P-M-Zuteilung�x� � x�Fähigkeit� � 4�<br />

Seite 76


Das Relationale Datenmodell<br />

Berechnung der Formeln des Tupelkalkül<br />

� Ein Ausdruck des Tupelkalküls hat die Form<br />

�t<strong>RS</strong> � � | ft ���<br />

wobei t (aus dem Schema <strong>RS</strong>) die einzig freie Variable in f ist.<br />

Definition (Substitution):<br />

� Sei fs � � eine Formel mit der freien Variable s. Dann ist fs/t � � die Substitution von der<br />

Tupelvariable s in f durch das Tupel t, falls in jedem Atom, das ein freies Auftreten<br />

von s enthält, wie folgt verfahren wird:<br />

– R(s) wird ersetzt durch “wahr”, falls t � R.<br />

Andernfalls durch “falsch”.<br />

– s[A] � u[B] wird ersetzt durch c � u[B] mit c = t[A] (Ann.: u�s )<br />

– s[A] � c wird ersetzt durch “wahr”, falls tA � � � c<br />

gilt. Andernfalls durch “falsch”.<br />

Bemerkung:<br />

� Durch Substitution gewinnt man eine Formel die nur noch Konstanten der Form<br />

“wahr” und “falsch” und Atome mit gebundenen Variablen enthält.<br />

Seite 77


Beispiele<br />

� Voraussetzung:<br />

– u und t aus dem Schema {pnr,mnr, Fähigkeit}<br />

� Gegeben sei die Formel:<br />

�u��PM-Zuteilung(u)<br />

� �upnr<br />

� � = tpnr � � � u�Fähigkeit� � t�Fähigkeit�� Für das Tupel t = (73,84,5) gilt:<br />

�u��PM-Zuteilung(u)<br />

� �upnr<br />

� � = 73 � u�Fähigkeit� � 5�<br />

� Gegeben sei die Formel:<br />

�PM-Zuteilung(u) � �upnr<br />

� � = 73 � u�Fähigkeit��5 Für das Tupel u = (51,93,2) gilt:<br />

�wahr � �falsch<br />

�<br />

wahr<br />

Das Relationale Datenmodell<br />

Seite 78


Interpretation der Formel<br />

Das Relationale Datenmodell<br />

� Sei f eine Formel ohne freie Variablen. Die Interpretation I(f) ist wie folgt definiert:<br />

– Sei f = “wahr”. Dann ist I(f) := true. Sei f = “falsch”. Dann ist I(f) := false.<br />

– Sei f = (g). Dann ist I(f) := I(g).<br />

– Sei f = �g.<br />

Dann ist I(f) := true genau dann, falls I(g) = false.<br />

– Sei f = g � h.<br />

Dann ist I(f) := true genau dann, falls I(g) = true und I(h) = true.<br />

– Sei f = g � h.<br />

Dann ist I(f) := true genau dann, falls I(g) = true oder I(h) = true.<br />

– Sei f = �x<strong>RS</strong><br />

� � �gx � ��.<br />

Dann ist I(f) := true, falls es mindestens ein Tupel t aus dem<br />

Schema <strong>RS</strong> gibt, so dass I(g(x/t)) = true ist. Andernfalls, I(f) := false<br />

– Sei f = �x<strong>RS</strong><br />

� ��gx � ��.<br />

Dann ist I(f) := true genau dann, falls für alle t aus dem Schema<br />

<strong>RS</strong> I(g(x/t)) = true gilt. Andernfalls, I(f) := false.<br />

� Sei E = �x�<strong>RS</strong>� | fx � ��<br />

ein Ausdruck des Tupelkalküls und sei <strong>RS</strong> = {A1 ,…,An } das<br />

Schema von x und D1 � D2 � … � Dn der Wertebereich. Der Wert von E zu einer<br />

gegebenen Datenbank besteht aus allen Tupel t � D1�D2�… � Dn , die<br />

erfüllen.<br />

I�f�x/t�� =<br />

true<br />

Seite 79


Beispiele<br />

Das Relationale Datenmodell<br />

� Gib alle Personalnummern von Personen, die an einer Maschine ausgebildet sind.<br />

�t��pnr�� | �u�PM-Zuteilung�u�<br />

� u�pnr� = tpnr � ���<br />

� Gib alle Personalnummern der Personen, die an keiner Maschine genügend gut<br />

ausgebildet sind.<br />

�t��pnr�� | �u��PM-Zuteilung�u�<br />

� u�Fähigkeit� � 5 � �upnr<br />

� � = tpnr � ���<br />

Menge der möglichen Werte<br />

für u (t[pnr] = 1):<br />

P-M-Zuteilung<br />

u[pnr] = 1<br />

alle möglichen Werte<br />

für u<br />

Seite 80


�<br />

�<br />

�<br />

Beispiel<br />

Das Relationale Datenmodell<br />

Einführung von Kurzschreibweisen:<br />

�u � R�fu<br />

� ��<br />

:= �u�<strong>RS</strong>R��Ru � � � fu � ��<br />

�u � R�fu<br />

� ��<br />

:= �u�<strong>RS</strong>R���Ru � � � fu � ��<br />

f� g:=<br />

�f � g<br />

� Berechne die Namen der Personen, die an keiner Maschine genügend gut<br />

ausgebildet sind (Schema der Tupelvariablen t ist {PName}).<br />

�t | �x � Personalf�x�t�� � �y��pnr���ypnr<br />

� � = xpnr � � � gy � ���<br />

– fxt � � � = �xPName � � = tPName � ��<br />

–<br />

gy � � = �u<br />

� PM-Zuteilung�u�Fähigkeit�<br />

� 5 � �u�pnr�<br />

= ypnr � ��<br />

Vereinfachen der Formel g:<br />

gy � � =<br />

�u<br />

� PM-Zuteilung��upnr<br />

� � = ypnr � ��<br />

� �u�Fähigkeit� � 5��<br />

Seite 81


Sichere Ausdrücke<br />

Das Relationale Datenmodell<br />

� Probleme des Tupelkalküls:<br />

– Beschreibung unendlich großer Relationen<br />

– Keine effektive Berechnung möglich (d.h. nur durch Testen jedes Elements aus dem<br />

Wertebereich)<br />

� Idee:<br />

– Beschränkung der Wertebereiche nur auf die tatsächlich in den vorhandenen Instanzen<br />

(der Relationen) vorkommenden Werte.<br />

� Definition: DOM�� f<br />

Menge aller Werte, die explizit in f vorkommen, oder in Instanzen der Relationen, die in f<br />

erwähnt werden (zur Erinnerung: Instanzen sind hier stets endlich).<br />

– Beispiel: f = “t�2� = 7 � Rt ��“ mit .<br />

Dann gilt:<br />

DOM�� f =<br />

�ab � � � �357 � � �<br />

R<br />

a 5<br />

b 3<br />

Seite 82


Definition (sicherer Ausdruck)<br />

Ein Ausdruck �t(<strong>RS</strong>) ft ���<br />

wird als sicher bezeichnet, falls:<br />

1.<br />

2. für jede Teilformel �u�gu � ��<br />

gilt: I�gu � � v��<br />

= true � v � DOM�g� 3. für jede Teilformel �u�gu � ��<br />

gilt: v � DOM�g��I�gu � � v��<br />

= true<br />

Beispiele:<br />

�<br />

�<br />

�t�<strong>RS</strong>Personal� | Personal�� t � t�Vorname� = “Willi“ �<br />

ist ein sicherer Ausdruck<br />

�t�<strong>RS</strong>Personal� | �Personal�� t � tVorname � � = “Willi“ ��<br />

ist nicht sicher.<br />

Das Relationale Datenmodell<br />

� Für eine Relation R und eine Formel f erfüllen die folgenden Teilformeln die<br />

Bedingung 2 bzw. 3:<br />

– �u � R�fu<br />

� ��<br />

–<br />

I�fu � � t��<br />

= true � t � DOM�� f<br />

�u � R�fu<br />

� ��<br />

Seite 83


3.4.2 Das Bereichskalkül<br />

Das Relationale Datenmodell<br />

� Das Bereichskalkül basiert auf einer ähnlichen Idee wie das Tupelkalkül mit dem<br />

Unterschied, dass Variablen sich jetzt auf die Komponenten der Tupel beziehen.<br />

� Ausdrücke haben die Form:<br />

�x1�xkfx � 1� �� xk�� wobei die Bereichsvariable x i einem Attribut A i zugeordnet ist, 1 � i � k. Die Bereichsvariablen<br />

x 1 ,…,x k sind die einzigen freien Variablen.<br />

Beispiele:<br />

�<br />

�vwxyz| � � � � Personalvwxyz � � � � � � mit x = “Willi“ �<br />

oder kürzer<br />

vw“Willi“ � � � yz| � Personal�v�w �“Willi“ � yz � ��<br />

oder wenn nur der Nachname erwünscht ist:<br />

�w | �v �y �z Personal�v�w �“Willi“ �yz � ��<br />

Seite 84


� Atome haben die Form:<br />

– Rx � 1�x k�<br />

(oder auch Rx � 1� �� xk�) – x � y mit Bereichsvariablen x und y<br />

� Substitution wird entsprechend wie beim Tupelkalkül vorgenommen<br />

Beispiele:<br />

Das Relationale Datenmodell<br />

� Was sind die Namen von Personen, die an einer Maschine ausgebildet sind.<br />

�t | �uvwxyzPM-Zuteilung<br />

� � � � � � �uvw � � ��Personal�u� t� x� y� z���<br />

� Was sind die Personalnummern der Personen, die an keiner Maschine genügend gut<br />

ausgebildet sind.<br />

�t | �x<br />

�y<br />

��PM-Zuteilung�txy � � � � y � 5��<br />

Seite 85


Das Relationale Datenmodell<br />

3.5 Erweiterung der relationalen Algebra<br />

Probleme der relationalen Algebra und des Tupelkalküls<br />

� Das bisherige Konzept der relationalen Algebra unterstützt zwar die Formulierung vieler<br />

wichtiger Anfragen. Folgende Anfragen können jedoch bisher nicht ausgedrückt werden:<br />

(i) Sortieren der Daten (insbesondere beim Ergebnis einer Anfrage)<br />

(ii) Abspeichern von Duplikaten (die z. B. durch Projektion entstehen)<br />

– Datentyp Relation (Menge von Tupeln) ist hierfür nicht ausreichend<br />

(iii) Verdichtung der Daten einer Relation durch Aggregation (Summe, Durchschnitt)<br />

– Fehlende Operatoren in der relationalen Algebra<br />

Beispielsanfragen<br />

� Berechne zu jeder Maschine die Anzahl von Personen, welche die Maschine bedienen können.<br />

� Wieviel Lohn muss diesen Monat an alle Angestellten gezahlt werden?<br />

Anmerkung<br />

� Wir werden später bei der tatsächlichen Anfragesprache relationaler Systeme (SQL) sehen,<br />

dass diese Anforderungen beim Entwurf von SQL berücksichtigt wurden.<br />

Seite 86


M-Relation<br />

Das Relationale Datenmodell<br />

� Eine Multi-Relation (M-Relation) R besteht aus einem Relationenschema <strong>RS</strong> R und einer<br />

Instanz I R , wobei I R eine Multimenge (auch als Bag bezeichnet) ist.<br />

– Das Schema einer M-Relation enstpricht dem einer gewöhnlichen Relation.<br />

– Die zu einer Multi-Relation gehörende Instanz wird durch eine Funktion VM (x)<br />

beschrieben, die zu jedem Tupel x die Häufigkeit von x in der derzeitigen Instanz liefert.<br />

� Notation<br />

– Um den Unterschied zu Mengen klar zu machen, verwenden wir statt Mengenklammern<br />

“”.<br />

� Zwei M-Relationen heißen schemaverträglich, falls die Attribute der Schemata gleich sind,<br />

und der Wertebereich der Attribute in beiden Relationen gleich ist.<br />

� Um die Semantik von Operationen zu definieren, verwenden wir die Funktionen V. Seien M<br />

und N schemaverträgliche M-Relationen. Dann gilt<br />

– M = N genau dann, falls � x:<br />

VM�x� = VN�x�. – M�N genau dann, falls � x:<br />

VM�x� �<br />

VN�x�. � Gewöhnliche Relationen können als Spezialfall von M-Relationen betrachtet werden, für deren<br />

Tupel x stets V M(x) � 1 gilt.<br />

Seite 87


Das Relationale Datenmodell<br />

Erweiterung der relationalen Operatoren<br />

� Selektion: MRel -> MRel<br />

–<br />

<strong>RS</strong>�F�R� = <strong>RS</strong>R – Es gilt: V�F�R� .<br />

– Die Selektion auf M-Relationen entspricht damit der Selektion auf Relationen.<br />

– Beispiel: Sei <strong>RS</strong>R = {A,B} und . Dann ist<br />

x � �<br />

�<br />

= �<br />

�<br />

VR�x� 0<br />

falls F�x� sonst<br />

= ��11 � ���12 � ���13 � ���12 � ��<br />

I�B = 2�R�<br />

= 12 �<br />

�� ���12 � ��<br />

I R<br />

� Kartesisches Produkt: MRel x MRel -> MRel<br />

– <strong>RS</strong>R � S = <strong>RS</strong>R � <strong>RS</strong>S (Ann.: <strong>RS</strong>R � <strong>RS</strong>S = �).<br />

– VR � S�x�<br />

= VR�x<strong>RS</strong> � R��<br />

� VS�x<strong>RS</strong> � S��<br />

für x�dom�R�S�. Es wird analog zu Mengen das kartesische Produkt bei Multimengen gebildet.<br />

– Beispiel: IR = ��1�� �2���1�� und IS = ��1���2��. Dann ist<br />

=<br />

��11 � ���12 � ���21 � ���22 � ���11 � ���12 � ��<br />

.<br />

IR � S<br />

Seite 88


Das Relationale Datenmodell<br />

� Vereinigung: MRel x MRel -> MRel<br />

– Seien R und S schemaverträglich.<br />

– Die Instanz ergibt sich aus folgender Bedingung: VR � S �x� +<br />

Bei der Vereinigung werden also Duplikate nicht beseitigt.<br />

= VR�x�+ VS�x�. – Beispiel: Seien IR = ��1�� �2�� �1�� und IS = ��2���3��. Dann ist<br />

= ��1�� �2�� �1�� �2���3��. IR �+<br />

S<br />

– Diese Vereinigung wird auch als Summenvereinigung bezeichnet. Zusätzlich wird auch<br />

noch die Maximumsvereinigung benötigt.<br />

� Differenz: MRel x MRel -> MRel<br />

– Annahme: R und S sind schemaverträglich. Somit ist <strong>RS</strong>R – S = <strong>RS</strong>S �= <strong>RS</strong>R�. – Die Instanz ergibt sich aus folgender Bedingung:<br />

� V<br />

– VR – S�x�<br />

R�x� – VS�x� falls VR�x� � VS�x� =<br />

�<br />

.<br />

� 0 sonst<br />

Die Differenz entfernt somit nicht alle Instanzen von einem Element aus der ersten<br />

Multimenge, das in der zweiten Multimenge vorkommt.<br />

Seite 89


– Beispiel: IR = ��2���1���2���1�� und IS = ��2���3�� . Dann ist<br />

= ��2�� �1�� �1�� .<br />

IR – S<br />

Das Relationale Datenmodell<br />

– Als Alternative könnte man auch die Differenz strikt definieren, indem jedes Tupel aus<br />

der Relation R entfernt wird, das in der Relation S liegt.<br />

� Projektion: MRel -> MRel<br />

– Das Relationenschema X der Projektion auf einer Relation R wird explizit beim<br />

Operationsaufruf definiert, wobei X � <strong>RS</strong>R. – Es gilt: . Bei der Projektion wird also jedes<br />

� � VR x'<br />

=<br />

� �<br />

V�X�R� x<br />

�<br />

x' � IR � x'�X� = x<br />

Tupel der Eingabe in ein Tupel der Ausgabe überführt. Gleiche Tupel werden<br />

verschmolzen und deren Vielfachheit aufsummiert.<br />

– Beispiel: Für IR = ��11 � �� �12 � �� �23 � ��<br />

ist I�1�R� =<br />

��1���1���2��. � Umbenennung: MRel -> MRel<br />

Entspricht der Operation, wie sie für Relationen definiert ist.<br />

Seite 90


Verallgemeinerung der Projektion<br />

Das Relationale Datenmodell<br />

� Die Projektion und auch die Umbenennung sind bei M-Relationen Operatoren, die zu jedem<br />

Tupel der Eingabe ein Tupel der Ausgabe erzeugen. Solche Abbildungen werden auch als map<br />

bezeichnet.<br />

� Seien R eine M-Relation, <strong>RS</strong> ein Relationenschema mit Wertebereich D und<br />

f: (<strong>RS</strong>R -> dom(R)) -> (<strong>RS</strong> -> D) eine Abbildung. Dann wird durch<br />

T = �f�R� die relationale Map definiert, wobei<br />

–<br />

–<br />

<strong>RS</strong>�f�R� = <strong>RS</strong><br />

V�f�R� x<br />

�<br />

� � VR y<br />

=<br />

� �<br />

y � IR�x= fy ()<br />

�<br />

Beachte, dass f eine Funktion ist, die ein Tupel der Relation R auf ein Tupel der<br />

Ergebnisrelation abbildet. Dabei nutzen wir die Definition des Tupels als eine Abbildung.<br />

Beispiel<br />

Sei R eine Relation mit <strong>RS</strong>R = {A,B} und IR = ��12 � ���21 � ���12 � ���21 � ���46 � ��.<br />

Sei f(t)<br />

= (t[A]*t[B], t[A] + t[B]) eine Abbildung. Dann ist<br />

·<br />

=<br />

�� � ���23 � ��<br />

�23 � �� �23 � �� �24� 10��.<br />

I�f�R� 23<br />

Seite 91


Motivation<br />

Aggregation<br />

Das Relationale Datenmodell<br />

� Um schnell einen Überblick der Daten einer Multi-Relation zu bekommen, soll in einer<br />

Anfragesprache auch die Berechnung wichtiger Kennzahlen unterstützt werden. Insbesondere<br />

im betriebswirtschaftlichen Umfeld sind dabei die Aggregationsoperationen Summe (sum),<br />

Durchschnitt (avg), Anzahl (count), Minimum (min) und Maximum (max) von Bedeutung.<br />

� In der relationalen Algebra sind solche Operationen bisher noch nicht berücksichtigt worden.<br />

Erweiterung der relationalen Algebra<br />

� Eine Aggregationsfunktion agg berechnet zu einer Multi-Relation einen Wert aus einem<br />

Wertebereich D. Ganz allgemein ist agg: MRel � D.<br />

� Die relevanten Aggregationsfunktionen sind avg, sum, count, min, max: MRel �<br />

D , die eine<br />

Multi-Relation auf den Wert eines Attributs abbilden.<br />

– Bei sum, avg, min und max muss noch zusätzlich ein Attribut aus dem Schema der<br />

Relation angegeben werden, auf welches das Aggregat angewendet wird.<br />

– Die Operation count liefert die Anzahl der Tupel in der Instanz der Relation.<br />

� Aggregate finden zunächst nur Verwendung in Kombination mit einem Gruppierungsoperator,<br />

den wir auf der folgenden Seite einführen.<br />

Seite 92


Gruppierung<br />

Das Relationale Datenmodell<br />

� Um gleich mehrere Kennzahlen für eine Multi-Relation zu berechnen, kann diese in Klassen<br />

(Partitionen) aufgeteilt und für jede dieser Partitionen eine Kennzahl berechnet werden.<br />

� Eine Partition ist wiederum eine Relation, die das Schema von der Quelle erbt.<br />

– Bei einer Relation R wird eine Partitionierung durch �A1, �,<br />

An��<strong>RS</strong>R definiert. Eine<br />

Partition enthält alle Tupel aus IR , die bzgl. der Attribute �A1, �,<br />

An� den gleichen Wert<br />

besitzen.<br />

� Zu einer Aggregatoperation (und einem ausgezeichneten Attribut) wird nun für jede Partition<br />

eine Kennzahl berechnet. Diese Kennzahl wird zusammen mit den Werten der<br />

Partitionierungsattribute in der Ergebnisrelation eingetragen.<br />

� Sei R eine Multi-Relation und A = �A1, �,<br />

An��<strong>RS</strong>R. Des Weiteren seien B1 ,…,Bm Attribute und agg1 ,…,aggm Aggregatsfunktionen mit aggi : MRel � dom( Bi) .Dann ist der<br />

Gruppierungsoperator S = �A B1<br />

( ) folgendermaßen definiert:<br />

� = agg1�…�Bm= agg R<br />

m<br />

– <strong>RS</strong>S = A��B1�…�Bm�.(Ann.: Bi � A,<br />

1 � i� m)<br />

� 1falls V<br />

– VS�x� R�xA � ��<br />

� 0<br />

= �<br />

und x[Bi ] = aggi ( �RA � � = xA � ��R�).<br />

� 0 sonst<br />

Seite 93


Beispiel:<br />

� Betrachten wir die Relationeninstanz IR = ��ax � ���ay � ���az � ���bu � ��<br />

. Dann ist<br />

( R)<br />

= ��a� 3���b�<br />

1��.<br />

Es treten also keine Tupel mehrfach auf.<br />

�A�C = count<br />

Spezialfall (Duplikateliminierung)<br />

Das Relationale Datenmodell<br />

� Ein wichtiger Spezialfall des Gruppierungsoperators ist die Duplikateliminierung �.<br />

Dabei<br />

setzen wir A = <strong>RS</strong>R und berechnen keine Aggregationsfunktion (m=0).<br />

� Durch eine Duplikateliminierung werden alle Zähler von Tupeln der Relation R auf den Wert 1<br />

gesetzt. Eine solche Multi-Relation entspricht einer gewöhnlichen Relation.<br />

� Beispiele:<br />

– Sei R = ��1�� �2�� �1�� eine M-Relation. Dann ist ��R� = ��1���2��. – Relationenschemata:.<br />

Berechne die Abteilungen, in denen Mitarbeiter in der Lohngruppe L6 oder höher sind.<br />

�� � Abt��Lohn � L6�Personal���<br />

Seite 94


Abgeleitete Operationen<br />

Das Relationale Datenmodell<br />

� Man hat bereits bemerkt, dass die Unterstützung von Multi-Relationen zu einem wesentlich<br />

komplexeren Modell führt.<br />

– Insbesondere gelten die Mengengesetze für die Instanzen der Multi-Relationen nicht.<br />

� Deshalb werden noch weitere Operationen für die Vereinigung und Differenz benötigt.<br />

– Schnitt zweier schemaverträglicher Relationen R und S<br />

– Maximumsvereinigung von R und S<br />

– Strikte Differenz<br />

R�S = R– �R – S�<br />

R�maxS = �R– S�<br />

�+<br />

S<br />

R-strictS =<br />

R ��( R)<br />

– S�<br />

� Anmerkung<br />

Leider ist dieser Grad an Präzision notwendig, da nur dadurch die Semantik von Anfragesprachen<br />

wie SQL klar definiert werden kann.<br />

Seite 95


Beispiele<br />

� Wie beziehen uns auf die Datenbank mit den Relationen Personal, Maschinen, …<br />

Anfragen<br />

Das Relationale Datenmodell<br />

� Was ist die durchschnittiche Bewertung aller Angestellten an den zugeteilten Maschinen.<br />

� Wie sieht der Notenspiegel insgesamt aus?<br />

� Welche Maschine wird unter allen Maschinen am schlechtesten bedient?<br />

� Welcher Angestellte hat den besten Notendurchschnitt?<br />

� Berechne für jede Abteilung die Anzahl der Maschinen, die von den Mitarbeitern bedient<br />

werden können.<br />

� Was ist der Notendurchschnitt der Angestellten aus den verschiedenen Abteilungen?<br />

Seite 96


� Eine S-Relation besteht aus (R, < R ), wobei<br />

– R eine M-Relation<br />

– < R eine Ordnungsrelation auf dom(R)<br />

� Durch<br />

– : MRel -> SRel<br />

� <<br />

S-Relation<br />

wird eine M-Relation R auf eine S-Relation S = (R,


Seien<br />

– < 1 = {((a,b,c), (d,e,f)) | a < d}<br />

– < 2 = {((a,b,c), (d,e,f)) | c < f oder (c = f) und b > e}<br />

Ordnungsrelationen. Dann sind<br />

Achtung:<br />


Zusammenfassung<br />

� Begriff der Relation<br />

– Relationenschema und Relationeninstanz<br />

– Zwei Definitionen basierend auf Attributlisten und Attributmengen<br />

– Einfache Integritätsbedingungen<br />

� Abbildung von ER-Modell in ein relationales Modell<br />

Grundlagen von Anfragesprachen<br />

� Relationale Algebra<br />

– Mengenalgebra<br />

� Tupelkalkül<br />

– Prädikatenlogik erster Stufe<br />

� Erweiterte relationale Algebra<br />

– Algebra für Multimengen<br />

– Geordnete Mengen<br />

– Weitere Operationen: Aggregation, Gruppierung, Sortierung<br />

Das Relationale Datenmodell<br />

Seite 99


SQL: Die Sprache relationaler DBMS<br />

4. SQL: Die Sprache relationaler DBMS<br />

� Basierend auf dem Tupelkalkül und der relationalen Algebra wurden mit dem Aufkommen<br />

relationaler DBMS auch spezielle Sprachen entwickelt.<br />

– SQL ist die derzeit marktbeherrschende Anfragesprache<br />

– Von praktischer Bedeutung waren auch noch bis Ende der 80er Jahre:<br />

a) QBE (Query by Example, basierend auf dem Domainkalkül)<br />

b) Quel (Anfragesprache von Ingres basierend auf dem Tupelkalkül).<br />

Bei Anfragesprachen wird unterschieden zwischen der<br />

� Datendefinitionssprache (DDL)<br />

– Anlegen und Ändern der Datenstrukturen für die drei Ebenen einer Datenbank (externe<br />

Ebenen, konzeptionelle Ebene, physische Ebene)<br />

– Festlegen von Integritätsbedingungen<br />

– Festlegen der Zugriffsrechte<br />

� Datenmanipulationssprache (DML)<br />

– Einfügen, Ändern und Löschen von Datenobjekten<br />

– Anfragen<br />

Seite 100


Historie<br />

SQL: Die Sprache relationaler DBMS<br />

� SQL (structured query language) wurde bei IBM als Sprache des relationalen DBMS System R<br />

entwickelt (1974, D.D. Chamberlin et al.)<br />

– SQL ist eine Mischform aus der erweiterten relationalen Algebra und dem (erweiterten)<br />

Tupelkalkül.<br />

� Heute ist SQL quasi der Standard für Sprachen relationaler DBMS<br />

– SQL1, 1985<br />

– SQL2, 1992 (wird auch als SQL92 bezeichnet)<br />

– SQL3 (SQL:1999 und SQL 2003)<br />

� SQL wird als interaktive Sprache eingesetzt, kann aber auch durch eine geeignete Kopplung in<br />

einer Programmiersprache wie z. B. C und Java genutzt werden.<br />

Anmerkung<br />

� Das <strong>of</strong>fizielle Dokument, in dem der Standard von SQL beschrieben wird, umfaßt mehrere<br />

1000 Seiten. In dieser Vorlesung beschränken wir uns deshalb auf die wichtigsten Konzepte<br />

von SQL.<br />

� Viele Hersteller wie Oracle, Micros<strong>of</strong>t, IBM, … haben in ihren Systemen Erweiterungen von<br />

SQL implementiert.<br />

Seite 101


Lexikalische Elemente<br />

SQL: Die Sprache relationaler DBMS<br />

� Wie jede andere Programmiersprache besitzt SQL lexikalische Elemente.<br />

– Leerzeichen, Zeilenumbruch und Tabulatoren trennen lexikalische Elemente.<br />

Bezeichner<br />

� Bezeichner werden benutzt, um Namen an Datenbanken, Relationen und Attribute zu<br />

vergeben.<br />

� Aufbau eines Bezeichners<br />

– Erstes Zeichen ist ein Buchstabe.<br />

– Weiterhin können darin Zahlen und _ enthalten sein.<br />

– Bezeichner müssen sich von einem Schlüsselwort unterscheiden.<br />

Konstanten (Literale)<br />

� Literale sind sehr ähnlich zu den Konstanten in bekannten Programmiersprachen.<br />

� Gewöhnungsbedürftig sind Konstanten von Zeichenketten:<br />

– ´Gerd´ ist eine Konstante.<br />

– Einige DBMS unterstützen auch andere Formate.<br />

Seite 102


Vorbemerkungen<br />

4.1 DDL<br />

SQL: Die Sprache relationaler DBMS<br />

� Im Folgenden werden nun einige wichtige Aspekte bei der Datendefinition erläutert ohne<br />

jedoch auf viele der angebotenen Optionen einzugehen.<br />

� Wir werden beispielhaft die Definition von Datenstrukturen der konzeptionellen Ebene<br />

(Relation) erläutern<br />

– Die Definition von Datenstrukturen der internen Ebene (Index) und der externen Ebene<br />

(View) erfolgt später.<br />

Aufbau des Kapitels:<br />

� Datentypen<br />

� Definition von Relationen<br />

� Einfache Integritätsbedingungen<br />

Seite 103


4.1.1 Datentypen<br />

SQL: Die Sprache relationaler DBMS<br />

� Datenbanksysteme bieten eine sehr reichhaltige Palette von Datentypen an, die sich bis auf<br />

einen Kern erheblich unterscheiden.<br />

– Zum Teil findet man gleiche Datentypen mit unterschiedlichen Namen.<br />

– Auch wenn die Namen gleich sind, werden nicht die gleichen Operationen angeboten<br />

oder unterschiedliche Namen für die gleiche Methode.<br />

� Heutige Systeme unterstützen auch die Definition benutzerdefinierter Datentypen<br />

� Klassifizierung<br />

– Zeichenketten<br />

– Zahlen<br />

– Individuelle Erweiterungen, die es in nahezu allen DBMS gibt:<br />

binäre Daten (BLOB), Texte (CLOB), Date<br />

– DBMS spezifische Datentypen<br />

� Die unterschiedlichen Datentypen tragen insbesondere dazu bei, dass eine Kopplung von SQL-<br />

Datenbanken nicht so einfach ist.<br />

Seite 104


Zeichenketten<br />

Standardtypen<br />

SQL: Die Sprache relationaler DBMS<br />

� char(size) Zeichenkette mit konstanter Länge size<br />

– Maximallänge ist abhängig vom System.<br />

– char spezifiziert eine Zeichenkette mit einem Zeichen.<br />

� varchar(size) variabel lange Zeichenkette mit maximaler Länge size<br />

– Bedarfsorientierter Speicherplatzverbrauch<br />

� Die maximale Größe für size hängt von dem spezifischen DBMS ab, z. B. 8000 bei SQL<br />

Server. Wird size nicht angegeben, so hat die Zeichenkette die Länge 1.<br />

� Unicode-Unterstützung durch spezielle Typen: nchar, nvarchar<br />

Operationen auf Zeichenketten<br />

� Relationale Operatoren: =, , sind in allen DBMS verfügbar, aber die Semantik<br />

kann in Abhängigkeit des <strong>Systems</strong> anders sein. (Stichwort: Nullwerte)<br />

� Weitere Operatoren im SQL92 Standard (der aber in dieser Form nicht von allen DBMS<br />

unterstützt wird):<br />

– || ist z. B. die Verknüpfung von zwei Zeichenketten<br />

Seite 105


Zahlen<br />

� numeric(g,d) bzw. decimal(g,d)<br />

– Gleitkommazahlen mit: g = #Gesamtstellen, d = #Nachkommastellen<br />

� Darüber hinaus gibt es die üblichen Datentypen:<br />

integer, smallint, real, double precision<br />

� Operationen<br />

– *, /, +, -<br />

– und noch viele andere. Z. B.: abs<br />

Spezielle Datentypen<br />

SQL: Die Sprache relationaler DBMS<br />

� Die oben genannten Datentypen sind in ihrer Größe erheblich eingeschränkt. Anfang der 90er<br />

Jahre wurde dieses Defizit durch Einführung neuer Datentypen gemildert.<br />

long:<br />

– variabel lange Zeichenkette mit maximal 2 GB.<br />

– erhebliche Einschränkungen bei der Anfragebearbeitung<br />

clob / blob: variabel lange Zeichenfolge / Bytefolge mit maximal 4 GB<br />

� date/time Datentypen für Datum und Uhrzeit<br />

– date unterstützt ein Datum bis zum Jahr 9999<br />

Seite 106


Definition neuer Datentypen<br />

SQL: Die Sprache relationaler DBMS<br />

� In SQL lassen sich neue Wertebereiche anlegen, indem bestehende Wertebereiche<br />

eingeschränkt werden.<br />

– Syntax:<br />

create domain [as] [] []<br />

– Beispiel:<br />

create domain Adresse varchar(50) default 'Marburg'<br />

� Weiterhin können Datentypen zur Laufzeit verändert<br />

– alter domain …<br />

und gelöscht werden:<br />

– drop domain Adresse<br />

Bemerkung<br />

� Es handelt sich hierbei um eine sehr eingeschränkte Form der Definition von Datentypen. Es<br />

ist dadurch z. B. nicht möglich, strukturierte Datentypen zu definieren.<br />

� Die Syntax dieses Befehls ist nicht für alle DBMS einheitlich.<br />

Seite 107


SQL: Die Sprache relationaler DBMS<br />

4.1.2 Anlegen eines Relationenschemas<br />

Eine stark vereinfachte Grammatik zur Definition einer Relation<br />

create table ([,] *)<br />

::= | <br />

::= [] [not null | unique]<br />

::= default | null<br />

� Die genaue Behandlung von Integritätsbedingungen erfolgt später. Im Weiteren werden wir<br />

einige Möglichkeiten exemplarisch erläutern.<br />

Folgende Beispiele basieren auf dem Datenbankschema von Seite 57.<br />

Seite 108


Beispiel:<br />

create table Abteilung(<br />

abtnr int primary key,<br />

aname varchar(10) not null unique)<br />

Anmerkungen zu den Integritätsbedingungen<br />

SQL: Die Sprache relationaler DBMS<br />

� unique drückt aus, dass dieses Attribut ein Schlüsselkandidat ist. Wird ein Schlüsselkandidat<br />

durch mehrere Attribute A 1 , …, A n gebildet, so wird dies durch die Integritätsbedingung<br />

unique (A 1 ,…,A n ) angegeben.<br />

� not null sagt aus, dass das Attribut explizit belegt werden muss. Es dürfen keine Null-Werte<br />

auftreten.<br />

� Durch primary key (A1 ,…,An ) wird festgelegt, dass die Attributmenge {A1 ,…,An } der<br />

Primärschlüssel der Relation ist.<br />

– Direkt hinter dem Attribut, wenn Primärschlüssel aus einem Attribut besteht.<br />

� Durch Angabe eines Defaultwertes wird beim Einfügen eines Tupels dieser Wert zur<br />

Initialisierung benutzt, wenn explizit keine Wertzuweisung vorgenommen wurde.<br />

Seite 109


Beispiel:<br />

– create table pmzuteilung(<br />

pnr int references Personal(pnr),<br />

mnr int references Maschinen(mnr),<br />

note int,<br />

constraint pk primary key (pnr,mnr))<br />

Anmerkungen zu den Integritätsbedingungen<br />

SQL: Die Sprache relationaler DBMS<br />

� Ein Fremdschlüssel kann über die Integritätsbedingung references angegeben werden. Damit<br />

wird sichergestellt, dass das Tupel mit dem Schlüssel tatsächlich in der Relation (in unserem<br />

Beispiel ist das die Relation Personal) existiert.<br />

– Beim Einfügen eines neuen Tupels muss deshalb eine entsprechende Überprüfung<br />

stattfinden (was zu einem hohen Berechnungsaufwand führen kann).<br />

– Entsprechend muss beim Löschen eines Tupels aus einer Relation geprüft werden, ob eine<br />

Referenz auf dieses Tupel existiert.<br />

� Für eine Integritätsbedingung kann mit dem Schlüsselwort constraint ein Name definiert<br />

werden, mit dem man die Bedingung temporär außer Kraft setzten kann.<br />

Seite 110


Beispiel (komplett)<br />

� Alle Relationen der Datenbank werden dann durch folgende Befehle angelegt:<br />

– create table Maschinen(mnr int primary key, mname varchar(10))<br />

– create table Personal(pnr int primary key,<br />

pname varchar(10) not null,<br />

vorname varchar(10),<br />

abtnr int references Abteilung(abtnr),<br />

lohn char(2) default 'L4')<br />

– create table leitet(pnr int primary key references Personal(pnr),<br />

abtnr int references Abteilung(abtnr))<br />

– create table Abteilung(abtnr int primary key, aname varchar(10))<br />

– create table pmzuteilung(pnr int references Personal(pnr),<br />

mnr int references Maschinen(mnr),<br />

note int,<br />

constraint pk primary key (pnr,mnr))<br />

Anmerkungen<br />

SQL: Die Sprache relationaler DBMS<br />

� Das Schlüsselwort default wird benutzt, um Attribute eines Tupel mit einem initialen Wert zu<br />

belegen.<br />

Seite 111


SQL: Die Sprache relationaler DBMS<br />

Ändern/Löschen eines Relationenschemas<br />

Ändern<br />

alter table add <br />

Besonderheiten<br />

� Prinzipiell sind Syntax und Semantik solcher Befehle stark von dem jeweiligen<br />

Systemhersteller abhängig.<br />

Löschen<br />

drop table <br />

Seite 112


4.2 DML - Grundkonzepte<br />

SQL: Die Sprache relationaler DBMS<br />

� Anfragen an die Datenbank werden in der DML formuliert<br />

� Grundschema:<br />

select < Liste von Attributsnamen > z.B. select PName<br />

from < ein oder mehrere Relationennamen > from Personal<br />

[ where < Bedingung > ] where Lohn = 'L5'<br />

Bemerkungen:<br />

� Die select-Klausel entspricht der Projektion in der relationalen Algebra (und nicht der<br />

Selektion).<br />

� Die Bedingung nach der where-Klausel enthält<br />

1. Vergleichsoperatoren (, = ... )<br />

2. Boolesche Operatoren (and, or , not)<br />

3. Mengenoperatoren (in, not in) und Quantoren (exists, any, some, all)<br />

� Attribute mit gleichen Namen, die zu verschiedenen Relationen gehören, werden mittels des<br />

Relationennamens unterschieden.<br />

Seite 113


SQL: Die Sprache relationaler DBMS<br />

4.2.1 Algebra-Operationen in SQL<br />

� Relation R<br />

select *<br />

from R<br />

Bei Angabe von “*” in der select-Klausel werden alle Attribute der Relation aus der from-<br />

Klausel ausgegeben.<br />

� Projektion<br />

select distinct A, C<br />

from R<br />

Ohne das Schlüsselwort distinct würde als Ergebnis eine M-Relation erzeugt werden.<br />

� Selektion<br />

�A�C �R� �B = b�R�<br />

select *<br />

from R<br />

where B = b<br />

Seite 114


� Kartesisches Produkt R�S select *<br />

from R, S<br />

� Theta-Join auf Relationen R(A,B) und S(C,D)<br />

R B�D S<br />

SQL: Die Sprache relationaler DBMS<br />

select *<br />

from R, S<br />

where B � D<br />

� Vereinigung der Relationen R(A,B) und T(A,B)<br />

select * from R<br />

union<br />

select * from T<br />

� Differenz der Relationen R und T<br />

select * from R<br />

except<br />

select * from T<br />

� Allgemeine Bedeutung der “select … from … where”-Klausel in der relationalen Algebra:<br />

select distinctA,B,C,..<br />

�<br />

from R,S,T,...<br />

A,B,C,�<br />

�� F<br />

�R�S�T���� where F<br />

Seite 115


Duplikate und M-Relationen<br />

SQL: Die Sprache relationaler DBMS<br />

� Die gewöhnliche select-Klausel beseitigt keine Duplikate in der Ergebnisrelation. Dies ist aber<br />

durch Hinzufügen des Schlüsselworts distinct möglich:<br />

select distinct A, B, C, …<br />

from R,S,T,…<br />

where Bedingung<br />

Durch distinct wird als Ausgabe eine Relation erzeugt. Ansonsten wird eine M-Relation ausgegeben.<br />

� Die Differenz auf zwei Multi-Mengen entspricht der Semantik, wie wir sie bereits bei der<br />

erweiterten relationalen Algebra kennen gelernt haben.<br />

– Das Schlüsselwort minus wird nur von Oracle benutzt. In SQL92 gibt es stattdessen das<br />

Schlüsselwort except.<br />

– except all entspricht der Summendifferenz der erweiterten relationalen Algebra<br />

– SQL Server bietet eine solche Operation derzeit nicht an. Diese kann aber durch<br />

enstsprechende Prädikate in der where-Klausel implementieren werden.<br />

� Bei der Vereinigung auf Relationen werden automatisch Duplikate beseitigt. Dies gilt auch für<br />

M-Relationen. Sollen Duplikate nicht beseitigt werden, muss hinter dem Schlüsselwort union<br />

das Schlüsselwort all folgen.<br />

Seite 116


Beispielanfragen<br />

Welche Angestellten sind in der Lohngruppe L4 oder L5?<br />

select distinct PName<br />

from Personal<br />

where Lohn = 'L4' or Lohn = 'L5'<br />

SQL: Die Sprache relationaler DBMS<br />

Welche Angestellten können irgendwie die Maschine mit Nr. 84 bedienen?<br />

select distinct PName<br />

from Personal, PMZuteilung<br />

where Personal.pnr = PMZuteilung.pnr and mnr = 84<br />

Seite 117


4.2.2 From-Klausel<br />

SQL: Die Sprache relationaler DBMS<br />

� Innerhalb einer From-Klausel können auch Tupelvariablen definiert werden.<br />

…<br />

from PMZuteilung L /* L Ist eine Tupelvariable */<br />

…<br />

� Damit kann man nun über die Tupelvariable L die Attribute in der Relation ansprechen.<br />

– Dadurch kann eine Art “Umbenennung” der Relation erfolgen.<br />

select distinct P1.pnr, P2.pnr, P1.Fähigkeit<br />

from PMZuteilung P1, PMZuteilung P2<br />

where P1.mnr = P2.mnr and P1.pnr < P2.pnr<br />

– Die Unterscheidung der Attribute erfolgt durch Verwendung der Punkt-Notation. Dies ist<br />

nur dann erforderlich, wenn der Attributname nicht eindeutig einer Relation zugeordnet<br />

werden kann.<br />

� In einer from-Klausel können nicht nur physische Relationen angegeben werden, sondern auch<br />

wiederum Anfragen - man spricht dann von Unteranfragen - auftreten:<br />

select L1.PName<br />

from (select PName, pnr from Personal where Lohn = 'L4') L1<br />

In diesem Fall muss eine Tupelvariable benutzt werden.<br />

Seite 118


Joins in der From-Klausel<br />

SQL: Die Sprache relationaler DBMS<br />

� Die Joinbedingung kann sowohl direkt in der from-Klausel als auch in der where-Klausel<br />

angegeben werden. Letzteres wird in allen DBMS unterstützt.<br />

� Natural Join /* Wird nicht von Interbase, SQL Server, … unterstützt */<br />

… from R natural join S …<br />

oder<br />

… from R join S<br />

� �-Join<br />

(auch als inner join bezeichnet)<br />

… from R join S on A � B …<br />

� left outer join<br />

… from T left join S on A � B …<br />

� right outer join<br />

… from T right join S on A �<br />

B …<br />

Bemerkung<br />

� Der eigentliche Grund für diese Notation ist die Formulierung von äußeren Joins.<br />

Seite 119


4.2.3 Where-Klausel<br />

SQL: Die Sprache relationaler DBMS<br />

� In einer where-Klausel wird eine Boolesche Funktion angegeben, die im Wesentlichen einer<br />

Formel des Tupelkalküls entspricht.<br />

� Wir wollen zunächst einfache Formeln betrachten, die keine quantifizierten Teilformeln<br />

enthalten.<br />

Aufbau von einfachen Formeln<br />

� Einfache Formeln setzen sich aus Atomen der Form “A op B” zusammen,<br />

– Dabei steht op für ein Vergleichsoperator.<br />

– A und B stehen hier nicht nur für Attribute und Konstanten, sondern es können auch<br />

komplexere Ausdrücke sein.<br />

a) Bei numerischen Ausdrücken sind dies unter anderem die 4 arithmetischen<br />

Grundoperationen. Weiterhin kann hier auf die Vielzahl von im DBS angebotenen<br />

Operationen wie z. B. abs verwendet werden.<br />

b) Bei Zeichenketten umfaßt dies insbesondere die Verkettung “||”.<br />

� Atome können mit den Operatoren not, or und and zu komplexeren Formeln verknüpft werden.<br />

Seite 120


Weitere Varianten von atomaren Formeln:<br />

SQL: Die Sprache relationaler DBMS<br />

� Das Schlüsselwort and kommt nochmals als Bestandteil eines anderen Operators vor:<br />

– A between B and C<br />

– Diese Boolesche Funktion ist äquivalent zu B


Nullwerte<br />

SQL: Die Sprache relationaler DBMS<br />

� SQL benutzt zur Unterstützung von Nullwerten in Anfragen eine dreiwertige Logik.<br />

� Beispiel<br />

– Annahme: Es gibt ein Tupel (73, 101, NULL) in Relation PMZuteilung.<br />

– Sowohl select * from PMZuteilung where Fähigkeit > 2<br />

als auch select * from PMZuteilung where not Fähigkeit > 2<br />

�<br />

liefert uns nicht das Tupel als Ergebnis.<br />

Wir benötigen noch eine Möglichkeit, um Tupel mit Nullwerten zu finden. Dazu bedient man<br />

sich in SQL92 des Schlüsselworts is:<br />

– select * from PMZuteilung where Fähigkeit is null<br />

liefert die Tupel, deren Attribut Fähigkeit keinen Wert (also null) besitzt.<br />

Bemerkung<br />

� Man könnte auch ein relationales Modell ohne die Verwendung von NULL-Werten<br />

entwickeln.<br />

� NULL-Werte werden unterschiedlich in den kommerziellen DBMS verarbeitet.<br />

Seite 122


4.2.4 Select-Klausel<br />

SQL: Die Sprache relationaler DBMS<br />

� Die Select-Klausel wird als letztes bei der SQL-Anfrage ausgeführt.<br />

� Wurde eine Relation R berechnet, so werden durch<br />

select * …<br />

die Tupel mit allen Attributen der Relation R ausgegeben.<br />

� Entsprechend können alle Attribute einer am Join beteiligten Relation S durch<br />

select S.* from S,… where …<br />

ausgegeben werden.<br />

� Zur Wiederholung: select distinct beseitigt Duplikate, wohingegen select all dies nicht macht<br />

(select entspricht select all)<br />

Definition von Attributen im Ergebnis<br />

� Prinzipiell kann als Ergebnis in der select-Klausel ein Ausdruck stehen, der von mehreren<br />

Attributen abhängt. Man kann nun durch das Schlüsselwort as einer Spalte explizit einen neuen<br />

Namen zuweisen.<br />

select A*B as X from R<br />

Man kann dabei das Schlüsselwort as auch einfach weglassen.<br />

Seite 123


4.2.5 Aggregate<br />

SQL: Die Sprache relationaler DBMS<br />

� In SQL werden folgende Aggregatfunktionen angeboten: count, sum, avg, min und max.<br />

– Aggregate dürfen nur in der select-Klausel einer Anfrage auftreten. Man beachte, dass die<br />

select-Klausel zuletzt angewendet wird und dass zuvor eine Relation R als<br />

Zwischenergebnis bereits berechnet wurde.<br />

– Bei der Berechnung eines Aggregats wird eine Relation mit einem Tupel erzeugt.<br />

– Als Parameter eines Aggregats ist ein Ausdruck erlaubt. Das Aggregat count kann auch<br />

als Parameter einen “*” besitzen. Dann wird als Ergebnis die Anzahl der Tupel der<br />

Relation R geliefert.<br />

– Bei Angabe des Schlüsselworts distinct vor dem Ausdruck werden zunächst die Duplikate<br />

beseitigt, die durch Auswertung des Ausdrucks auf der Relation R entstehen. Danach wird<br />

das eigentliche Aggregat berechnet wird.<br />

� Die Aggregatfunktionen min, max und count können auf beliebige Ausdrücke angewendet<br />

werden. Die Funktionen sum und avg erwarten als Eingabe eine Zahl.<br />

– min bzw. max berechnet das Minimum bzw. das Maximum<br />

– count die Anzahl der Terme<br />

– sum berechnet die Summe aller Terme<br />

– avg berechnet den Durchschnitt über alle Terme.<br />

Seite 124


Beispiele<br />

� Wie viele Angestellte arbeiten in der Abteilung 'B10'?<br />

select count (pnr)<br />

from Personal<br />

where abtnr = 'B10'<br />

� Wie viele Angestellte mit verschiedenen Vornamen gibt es?<br />

select count (distinct Vorname)<br />

from Personal<br />

SQL: Die Sprache relationaler DBMS<br />

� Berechne die Anzahl der Angestellten, die Maschine 84 bedienen können, sowie deren<br />

durchschnittliche, minimale und maximale Fähigkeiten.<br />

select count(pnr), min(Fähigkeit), avg(Fähigkeit), max(Fähigkeit)<br />

from PMZuteilung<br />

where mnr = 84<br />

Seite 125


Nullwerte und Aggregate<br />

SQL: Die Sprache relationaler DBMS<br />

� Nullwerte werden bei der Berechnung eines Aggregats nicht berücksichtigt, mit Ausnahme<br />

von count(*).<br />

� Ist die Eingabe für das Aggregat leer, wird als Ergebnis null geliefert. Ausnahme ist wiederum<br />

count, das den Wert 0 zurückgibt.<br />

Seite 126


Gruppierung<br />

Allgemeinere Form der “select...from...where”-Klausel:<br />

select ..... from..... [where.....]<br />

[group by [,] *]<br />

[having < Bedingung>]<br />

[order by ]<br />

“group by”-Klausel<br />

SQL: Die Sprache relationaler DBMS<br />

� Diese wird nach der where-Klausel ausgeführt, aber noch vor der select-Klausel.<br />

� Zunächst werden anhand der Attribute in der Klausel Äquivalenzklasse gebildet.<br />

– Zwei Tupel sind in der gleichen Klasse, wenn diese bzgl. der in der Klausel spezifizierten<br />

Attribute gleich sind.<br />

� Pro Klasse wird dann durch die select-Klausel ein Tupel erzeugt. Die select-Klausel besteht<br />

dabei nur aus<br />

– Aggregaten, die dann auf die Gruppen angewendet werden.<br />

– Attributen, die bereits in der group_by-Klausel aufgetreten sind.<br />

Seite 127


Nullwerte<br />

SQL: Die Sprache relationaler DBMS<br />

� Wird für das group-by Attribut der Wert NULL angenommen, so wird eine entsprechende<br />

Gruppe eröffnet.<br />

“having”-Klausel<br />

� Filtern der durch die group_by-Klausel erzeugten Gruppen anhand einer Bedingung<br />

– Es dürfen nur Argumente mit einem Wert pro Gruppe auftreten.<br />

– Innerhalb einer having-Klausel sind Aggregate erlaubt (im Gegensatz zur where-Klausel)<br />

Beispiel:<br />

select mnr, avg(Fähigkeit)<br />

from PMZuteilung<br />

where Fähigkeit < 4<br />

group by mnr<br />

having count (*) > 4<br />

Seite 128


Order-By-Klausel:<br />

4.2.6 Geordnete Ausgabe<br />

order by A 1 [asc|desc] ,…, A n [asc|desc]<br />

SQL: Die Sprache relationaler DBMS<br />

� Durch diese Klausel wird die Ausgabe des SQL-Befehls sortiert ausgegeben, wobei die<br />

Sortierreihenfolge bzgl. den angegebenen Attributen erfolgt (absteigend: desc oder<br />

aufsteigend: asc).<br />

– Statt eines Attributs kann auch ein Ausdruck benutzt werden.<br />

– Sind mehrere Kriterien angegeben, so wird nach deren lexikographischer Ordnung<br />

sortiert.<br />

� Die order-by Klausel ist die letzte Klausel in einem SQL-Befehl.<br />

– Das Ergebnis der Klausel kann nicht weiterverarbeitet werden.<br />

� Null-Werte:<br />

Beim Sortieren wird null entweder stets als höchster oder kleinster Wert interpretiert<br />

(unabhängig ob asc oder desc angegeben wurde).<br />

– Welche der beiden Möglichkeiten gewählt wird, hängt vom zugrunde liegenden DBMS<br />

ab.<br />

Seite 129


Beispiele<br />

SQL: Die Sprache relationaler DBMS<br />

� Erstelle eine geordnete Liste aller Maschinen, in der für jede Maschine der minimale und der<br />

maximale Wert für die Fähigkeit der Angestellten angegeben sind!<br />

select mnr, min (Fähigkeit) as MinP, max (Fähigkeit) as MaxP<br />

from PMZuteilung<br />

group by mnr<br />

order by mnr<br />

� Welche Maschine kann von nur einem Angestellten bedient werden?<br />

select mnr<br />

from PMZuteilung<br />

group by mnr<br />

having count(*) = 1<br />

� Sortiere die Tupel aus PMZuteillung aufsteigend nach mnr und absteigend nach Fähigkeit!<br />

select *<br />

from PMZuteilung<br />

order by mnr, Fähigkeit desc<br />

Seite 130


4.2.7 Zusammenfassung<br />

SQL: Die Sprache relationaler DBMS<br />

� Eine SQL-Anfrage setzt sich aus folgenden Klauseln zusammen:<br />

select X<br />

from R r,S s,T t,...<br />

where F<br />

group by Y<br />

having G<br />

order by H<br />

� X eine Menge von Attributen<br />

– Optional können diese Attribute in der select-Klausel neu definiert und einen Wert eines<br />

Ausdrucks repräsentieren.<br />

� R,S,T,… eine Menge von Relationen und r,s,t,… eine Menge von Tupelvariablen<br />

– Tupelvariablen sind nur dann erforderlich, wenn statt einer Relation eine Unteranfrage<br />

angesprochen werden soll.<br />

� F eine Boolesche Formel<br />

� Y eine Menge von Attributen, wobei Y �<br />

X gilt.<br />

� G eine Boolesche Formel, die sich nur auf die Gruppen der group-by-Klausel bezieht.<br />

� H eine Liste von Attributen, die zum Sortieren des Ergebnis benutzt wird.<br />

Seite 131


4.3 Geschachtelte Anfragen<br />

SQL: Die Sprache relationaler DBMS<br />

� In einer SQL-Anweisung können in der<br />

– where-Klausel,<br />

– from-Klausel,<br />

– select-Klausel<br />

wieder SQL-Anweisungen auftreten. Man spricht dann auch von einer geschachtelten Anfrage<br />

oder Unteranfrage.<br />

� Bei Unteranfragen werden häufig Tupelvariablen benutzt.<br />

– Eine Tupelvariable wird in der from-Klausel deklariert und dabei einer Relation<br />

zugeordnet.<br />

– Tupelvariablen sind dann erforderlich, wenn die gleiche Relation mehrfach in einer<br />

Anfrage benutzt wird.<br />

Welche Angestellten können die gleiche Maschine bedienen?<br />

select distinct a1.pnr, a2.pnr<br />

from PMZuteilung a1, PMZuteilung a2<br />

where a1.mnr = a2.mnr and a1.pnr < a2.pnr<br />

Seite 132


SQL: Die Sprache relationaler DBMS<br />

Unteranfragen in der from-Klausel<br />

� Innerhalb einer from-Klausel kann statt einer Relation eine Unteranfrage benutzt werden.<br />

– Dann ist es ebenfalls möglich, eine Tupelvariable an diese Unteranfrage zu binden.<br />

� Bestimmte Anfragen lassen sich erst über solche Unterfragen formulieren:<br />

Beispiel<br />

– Wie viele Angestellte können eine Maschine im Durchschnitt bedienen?<br />

select avg(t.summe)<br />

from (select mnr, count(*) as summe from PMZuteilung group by mnr) t<br />

� Die having-Klausel kann dann sogar durch eine äquivalente where-Klausel ersetzt werden.<br />

Anfrage mit having-Klausel äquivalente Anfrage ohne having-Klausel<br />

select A, agg(B) as C select *<br />

from R from ( select A, agg(B) as C<br />

where FW from R<br />

group by A where FW<br />

having FH(C) group by A) t<br />

where FH(t.C)<br />

Seite 133


SQL: Die Sprache relationaler DBMS<br />

Unteranfragen in der select-Klausel<br />

� Einige Datenbanksysteme unterstützen auch Unteranfragen in der select-Klausel (z. B. SQL<br />

Server):<br />

– Damit ist es möglich nach einem Attribut zu gruppieren und gleichzeitig im Aggregat<br />

verschiedene where-Bedingungen zu berücksichtigen.<br />

– Beispiel:<br />

select pnr,<br />

(select count(*) from Personal A where A.pnr = B.pnr and Lohn < 'L5'),<br />

(select count(*) from Personal A where A.pnr = B.pnr and Lohn


SQL: Die Sprache relationaler DBMS<br />

Unteranfragen in der where-Klausel<br />

� In der where-Klausel wird dabei noch unterschieden, ob das Resultat der Unteranfrage einen<br />

skalaren Wert oder eine Relation zurückliefert. Wir betrachten zunächst den ersten Fall:<br />

Skalare Unteranfragen<br />

� Welche Maschinen, die von dem Angestellten mit Nr. 67 bedient werden können, kann dieser<br />

besser als im Durchschnitt bedienen?<br />

select mnr<br />

from PMZuteilung<br />

where pnr = 67 and Fähigkeit < ( select avg(Fähigkeit)<br />

from PMZuteilung)<br />

Skalare Unteranfragen mit Exists<br />

� In der where Klausel werden auch Unteranfragen erlaubt, die einen Booleschen Wert<br />

zurückliefern. Diese sind durch das Schlüsselwort exists gekennzeichnet. Dabei ist die<br />

Bedingung<br />

– exists <br />

wahr, falls die Unteranfrage nicht leer ist.<br />

Seite 135


SQL: Die Sprache relationaler DBMS<br />

� Welche Abteilungen haben Angestellten, die die Maschine 84 bedienen können?<br />

select distinct abtnr<br />

from Personal P<br />

where exists (select pnr<br />

from PMZuteilung<br />

where P.pnr = pnr and mnr = 84)<br />

Gültigkeit von Tupelvariablen in Unteranfragen<br />

� Bei dieser Unteranfrage wird Bezug genommen auf eine Tupelvariable, die in der äußeren<br />

Anfrage definiert wurde. Bei der Auswertung der Anfrage wird entsprechend so wie beim<br />

Tupelkalkül vorgegangen (“von außen nach innen”). Man spricht dann auch von einer<br />

korrelierten Unteranfrage.<br />

– Eine unkorrelierte Unteranfrage braucht nur einmal ausgewertet zu werden. Dagegen<br />

muss eine korrelierte Anfrage für jedes äußere Tupel ausgewertet werden.<br />

� Eine Tupelvariable ist in allen zugehörigen Unteranfragen gültig. Eine Redeklaration der<br />

gleichen Tupelvariable überdeckt die äußere Deklaration der Variablen.<br />

– Sucht man die Deklaration einer Tupelvariable geht man also von innen nach außen. Es<br />

wird die Deklaration benutzt, die zuerst gefunden wird (und alle anderen ignoriert).<br />

Seite 136


Mengenwertige Unteranfragen<br />

SQL: Die Sprache relationaler DBMS<br />

� Durch Verwendung vom Schlüsselwort in kann getestet werden, ob ein Attribut einen Wert in<br />

einer Menge annimmt (oder auch nicht)<br />

select pnr, PName<br />

from Personal<br />

where pnr in<br />

(select pnr from PMZuteilung)<br />

Wie kann die Anfrage formuliert werden, ohne dabei eine Unteranfrage zu benutzen?<br />

� Soll nun getestet werden, ob ein Attribut mit allen Elementen einer Menge in einer bestimmten<br />

Beziehung steht, kann das Schlüsselwort all benutzt werden.<br />

Suche für alle Maschinen die Angestellten mit den besten Fähigkeiten!<br />

select *<br />

from PMZuteilung L<br />

where Fähigkeit


Differenz durch Unteranfragen<br />

SQL: Die Sprache relationaler DBMS<br />

� Eine Differenz zwischen Relationen kann über except ausgedrückt werden (wird nicht von<br />

allen DBMS unterstützt) oder durch eine Unteranfrage mit not in und not exists.<br />

� Beispiele:<br />

Berechne alle Angestellten, die derzeit keine Maschine bedienen können.<br />

select *<br />

from Personal<br />

where pnr not in (select pnr from PMZuteilung)<br />

oder<br />

select *<br />

from Personal P<br />

where not exists (select pnr from PMZuteilung where pnr = P.pnr)<br />

Seite 138


Allquantifizierte Anfragen<br />

SQL: Die Sprache relationaler DBMS<br />

� Da �x���x�����x����x��, können alle Anfragen mit einem Allquantor in äquivalente<br />

Anfragen umgeformt werden, die nur noch Existenzquantoren besitzen.<br />

� Welche Angestellte können alle Maschinen bedienen, die Angestellter 114 bedienen kann?<br />

– Anfrage im Tupelkalkül ?<br />

– Anfrage in SQL<br />

select distinct pnr<br />

from PMZuteilung L<br />

where not exists( select mnr<br />

from PMZuteilung<br />

where pnr = 114 and<br />

not mnr in ( select mnr<br />

from PMZuteilung<br />

where pnr =L.pnr))<br />

Seite 139


Anfrage:<br />

SQL: Die Sprache relationaler DBMS<br />

Allquantifizierte Anfragen mit count<br />

� Welche Angestellte können alle Maschinen bedienen?<br />

select pnr<br />

from PMZuteilung<br />

group by pnr<br />

having count(*) = (select count(*) from (select distinct mnr from PMZuteilung) t)<br />

Seite 140


SQL: Die Sprache relationaler DBMS<br />

4.4 Ändern einer Relationeninstanz<br />

� Tupelweises Einfügen:<br />

insert<br />

into [( [, ] * )]<br />

values ( [, Konstante] * )<br />

oder mengenweises Einfügen<br />

insert<br />

into [( [, ] * )]<br />

select ... from ... where ....<br />

� Löschen:<br />

delete<br />

from <br />

[where ]<br />

� Verändern:<br />

update <br />

set = [, = ] *<br />

[where ]<br />

Seite 141


Beispiele<br />

SQL: Die Sprache relationaler DBMS<br />

� Füge den Angstellten 51 ein, dass er/sie die Maschine 84 mit Fähigkeit 2 bedienen kann.<br />

insert into PMZuteilung (pnr, mnr, Fähigkeit)<br />

values (51, 84, 2)<br />

� Verbessere die Fähigekeiten des Angestelllten 114 um 1!<br />

update Fähigkeit<br />

set Fähigkeit = Fähigkeit - 1<br />

where pnr = 114 and Fähigkeit > 1<br />

Seite 142


Motivation<br />

Rekursion<br />

SQL: Die Sprache relationaler DBMS<br />

� In unserer Datenbank können Angestellte Vorgestzte für andere Angestellte sein. Daraus ergibt<br />

sich eine Hierarchie von Vorgesetzten; das ist in der Praxis sehr <strong>of</strong>t der Fall!<br />

� Folgende Anfrage soll dann unterstützt werden:<br />

Berechne alle Vorgesetzten, der Angestellten mit Lohngruppe L6.<br />

select L.pnr<br />

from Personal P, Abteilungsleiter L<br />

where P.Abt = L.abtnr and P.Lohn = ’L6’<br />

Jetzt sollen noch die potentiellen Vorgesetzten der Vorgesetzten berechnet werden:<br />

select L.pnr<br />

from Personal P, Abteilungsleiter L<br />

where P.Abt = L.abtnr and<br />

P.pnr in (select L.pnr from Personal P, Abteilungsleiter L<br />

where P.Abt = L.abtnr and P.Lohn = ’L6’)<br />

� Die Berechnung aller direkten und indirekten potentiellen Vorgesetzten kann mit den bisher<br />

vorgestellten Mitteln jedoch in SQL nicht formuliert werden.<br />

Seite 143


Rekursion in Oracle<br />

SQL: Die Sprache relationaler DBMS<br />

� Erst im SQL3-Standard wurden Möglichkeiten geschaffen, rekursive Anfragen zu formulieren.<br />

– Wir werden später noch auf die spezielle Syntax von SQL 3 eingehen.<br />

� Zuvor gab es für spezielle rekursive Anfragen verschiedene Insellösungen von den Herstellern,<br />

wie z. B. eine Tiefensuche in Oracle:<br />

– In der Klausel start with wird der Ausgangspunkt der Tiefensuche angegeben, in unserem<br />

Fall: P.Lohn = ’L6’<br />

– Hinter der Klausel connect by wird angegeben, wie bei der Tiefensuche der Vorgänger<br />

mit dem Nachfolger (über das Schlüsselwort prior) verbunden wird.<br />

In Oracle könnte dann obige Anfrage folgendermaßen formuliert werden:<br />

select L.pnr<br />

from Abteilungsleiter L join Personal P on L.abtnr = P.Abt<br />

connect by P.Abt = prior L.pnr<br />

start with P.Lohn= ’L6’<br />

Seite 144


Indexe<br />

4.5 Anlegen anderer Strukturen<br />

SQL: Die Sprache relationaler DBMS<br />

� Indexe sind Bestandteile der physischen Ebene. Sie dienen “nur” zur Verbesserung der<br />

Anfragezeit und haben keinen Einfluss auf die Anfragesemantik.<br />

– Maß für die Effizienz in Datenbanken: Anzahl der Plattenzugriffe<br />

� Ein Index ist eine Instanz einer Indexstruktur.<br />

– In kommerziellen Systemen gibt es folgende Indexstrukturen:<br />

B+-Bäume und Hashverfahren.<br />

– B+-Bäume garantieren ähnlich wie AVL-Bäume logaritmische Zugriffskosten, sind aber<br />

im Gegensatz zu AVL-Bäume für die Indexierung von Daten auf dem Externspeicher<br />

entwickelt worden.<br />

– Eine detaillierte Diskussion der Beschreibung der Indexstrukturen erfolgt in Kapitel<br />

“Physische Datenorganisation” auf Seite 302.<br />

� Ein Index bezieht sich auf ein Attribut, bzw. eine Folge von Attributen<br />

– Bei mehreren Attributen werden diese lexikographisch miteinander verknüpft.<br />

Seite 145


Anlegen eines Index<br />

create [unique] index on <br />

( [] [,[]] * )<br />

::= Asc | Desc<br />

SQL: Die Sprache relationaler DBMS<br />

� unique: Für alle Attributsnamen sind keine zwei Tupel mit gleichen Werten in diesem Attribut<br />

erlaubt �<br />

Schlüsselbedingung ist erfüllt.<br />

� In Datenbanksystemen, wie z. B. Oracle, können noch weitere Optionen beim Erzeugen von<br />

Indexen angegeben werden.<br />

– Ein Clusterindex bestimmt die physische Ordnung der Daten.<br />

– Ein “gewöhnlicher” Index hat keinen Einfluss auf die Ordnung. Man spricht dann auch<br />

von einem Sekundärindex.<br />

Beispiel:<br />

create unique index PersonalIndex on Personal (PName,Vorname)<br />

Löschen eines Index<br />

drop index <br />

Seite 146


Sichten<br />

SQL: Die Sprache relationaler DBMS<br />

� Sichten entsprechen den externen DB-Schemata.<br />

� In relationalen Systemen werden Sichten als (abgeleitete) Relationen aufgefasst, die durch<br />

Anfragen definiert werden.<br />

Sichten anlegen:<br />

create view [([,] *)] as [with check<br />

option]<br />

Beispiel:<br />

create view Top_PMZuteilung as<br />

select * from PMZuteilung where Fähigkeit < 3<br />

with check option<br />

Sichten löschen:<br />

drop view <br />

Seite 147


SQL: Die Sprache relationaler DBMS<br />

Änderungsoperationen und Sichten<br />

� Prinzipiell ist es möglich Datensätze auch in eine Sicht einzufügen.<br />

– entsprechend auch zu löschen und zu ändern<br />

� Durch das Schlüsselwort with check option können nur Datensätze in eine Sicht eingefügt<br />

werden, die bei einer Suche auf der Sicht auch wieder gefunden werden können.<br />

– Dies ist die einzig sinnvolle Variante einer View.<br />

� Beim Einfügen eines Tupels in einer Sicht müssen die Basisrelationen angepasst werden. die<br />

zur Definition der Sicht benutzt wurden.<br />

– In einer Sicht werden keine Daten gespeichert!<br />

� Die Zuordnung zu den Basisrelationen ist aber nicht immer möglich!<br />

– z. B. wenn ein Attribut einer Sicht durch eine Aggregatfunktion berechnet wird.<br />

� Sichten sind in Oracle / Interbase veränderbar, wenn folgende Bedingungen gelten:<br />

– keine Aggregatfunktionen<br />

– keine Anweisungen mit distinct, group by, having, union und minus<br />

– from-Klausel enthält nur eine Relation<br />

– ein Schüssel der Basisrelationen muss in der select-Klausel enthalten sein.<br />

� Es gibt aber durchaus veränderbare Sichten, die aber nicht alle vier der oben genannten<br />

Bedingungen, erfüllen.<br />

Seite 148


Integritätsbedingungen<br />

4.6 Datenintegrität<br />

SQL: Die Sprache relationaler DBMS<br />

� Einschränkung der Datenbankzustände auf diejenigen, die tatsächlich nur in der realen Welt<br />

existieren können.<br />

� Integritätsbedingungen sind aus dem erstellten Datenmodell ableitbar (semantisch) und können<br />

deshalb bei der Erstellung des Schemas bereits angegeben werden. Folgende Vorteile ergeben<br />

sich:<br />

– Einmalige Angabe der Konsistenzbedingungen<br />

– Keine lästige Überprüfung der Konsistenzbedingungen durch die AWPs<br />

– Verzögerte Überprüfung der Integritätsbedingungen aus Effizienzgründen, z. B. bei einer<br />

Masseneingabe von Daten<br />

Zwei Klassen von Integritätsbedingungen<br />

� statische Bedingungen<br />

– sind definiert bzgl. Datenbankzuständen<br />

� dynamische Bedingungen<br />

– sind definiert bzgl. Zustandsänderungen<br />

Seite 149


4.6.1 Schlüssel<br />

Schlüssel in einer Relation (mittels primary key)<br />

SQL: Die Sprache relationaler DBMS<br />

� Syntax<br />

– Wenn der Schlüssel nur ein Attribut umfasst, kann primary key direkt an das Ende der<br />

Attributdeklaration geschrieben werden.<br />

– Wenn der Schlüssel mehrere Attribute umfasst, gibt es eine eigene Klausel<br />

primary key (A1 ,…,An )<br />

– Es gibt höchstens einen Primärschlüssel in einer Relation.<br />

� Semantik<br />

– Die als Primärschlüssel spezifizierten Attribute sind eindeutig.<br />

– Die Attribute dürfen nicht den Wert null annehmen.<br />

Schlüssel (mittels unique)<br />

� Syntaktisch wird nun das Schlüsselwort unique benutzt.<br />

� Semantik (SQL´92)<br />

– Im Gegensatz zum Primärschlüssel ist der Wert null bei unique-Attributen erlaubt.<br />

– Es können mehrere Tupel existieren, die im unique-Attribut den Wert null besitzen.<br />

Seite 150


4.6.2 Fremdschlüssel<br />

SQL: Die Sprache relationaler DBMS<br />

� Damit bezeichnet man Attribute, die zur Modellierung einer Beziehung benutzt werden.<br />

� Semantik:<br />

Seien R und S Relationen mit dem Schema <strong>RS</strong>R und <strong>RS</strong>S . Sei K ( � <strong>RS</strong>R ). Schlüssel von R<br />

(gekennzeichnet durch primary key). Dann wird F �<br />

<strong>RS</strong>S Fremdschlüssel von S genannt,<br />

falls zu jedem Datensatz s aus der Relation S eine der folgenden Bedingungen gilt:<br />

– s[F] = NULL<br />

– es gibt einen Datensatz r aus R, so dass s[F] = r[K] gilt.<br />

� Mögliche Probleme, wenn referentielle Integrität nicht erfüllt ist:<br />

– Angstelle arbeitet in einer Abteilung, die es nicht gibt.<br />

– Angestellte sind an Maschinen ausgebildet, die nicht existieren.<br />

� Definition einer Fremdschlüsselbedingung:<br />

KNr muss bereits in der Relation Personal vorher als Primärschlüssel oder mit dem Schlüsselwort<br />

unique gekennzeichnet worden sein.<br />

– create table PMZuteilung (pnr int,,…,<br />

foreign key(pnr) references Personal(pnr))<br />

oder<br />

Seite 151


– create table PMZuteilung(pnr int references Personal(pnr), …)<br />

oder<br />

– create table PMZuteilung(pnr int,,…,<br />

FK_PNR foreign key(pnr) references Personal(pnr))<br />

SQL: Die Sprache relationaler DBMS<br />

In diesem Fall wird die Bedingung mit dem Namen FK_PNR versehen, was insbesondere<br />

die Performance bei Änderungsoperationen verbessern kann.<br />

Seite 152


SQL: Die Sprache relationaler DBMS<br />

Einhaltung referentieller Integrität<br />

� In einer Relation, die eine Beziehung modelliert, sollte gewährleistet sein, dass die<br />

Fremdschlüssel mit Werten belegt sind.<br />

� Relationale Algebra:<br />

– Relation R mit Primärschlüssel K<br />

– Relation S mit Fremdschlüssel F (bezieht sich auf K)<br />

�<br />

F<br />

�S��� K<br />

�R� � Erlaubte Änderungen<br />

– Einfügen eines Tupels s in S, wenn sF � � � �<br />

K<br />

�R� – Verändern eines Attributwerts eines Tupels s aus S, wenn …<br />

– Verändern von rK � � eines Tupels r aus R, wenn �<br />

F = r�K� �S� =<br />

�<br />

– Löschen eines Tupels r aus R, wenn …<br />

Seite 153


SQL: Die Sprache relationaler DBMS<br />

Überwachung der referentiellen Integrität<br />

Defaulteinstellung<br />

� Löschen eines Tupels r aus einer Relation R ist i.A. nicht möglich, falls es noch Tupel aus<br />

anderen Relationen gibt, die über einen Fremdschlüssel an r gebunden sind.<br />

Kaskadierendes Löschen/Ändern<br />

� Wenn ein Tupel r aus einer Relation R gelöscht/geändert wird, können auch Datensätze aus<br />

anderen Relationen automatisch gelöscht/geändert werden, die sich über einen Fremdschlüssel<br />

auf das Tupel r beziehen.<br />

� Bei der Definition des Fremdschlüssels kann diese Einstellung mit aufgenommen werden:<br />

Setzen auf Null<br />

� Wird ein Tupel gelöscht, wird der Wert aller davon abhängigen Attribute auf null gesetzt.<br />

� create table PMZuteilung(<br />

pnr int constraint fk_personal references Personal(pnr)<br />

on delete cascade)<br />

on update set null,<br />

…<br />

)<br />

Seite 154


4.6.3 Zeitpunkt der Überprüfung<br />

SQL: Die Sprache relationaler DBMS<br />

� In SQL gibt es noch die Möglichkeit den Zeitpunkt der Überprüfung einer<br />

Integritätsbedingung zu beeinflussen.<br />

� Motivation<br />

– Eine Integritätsbedingung gewährleistet, dass die durchschnittlichen Fähigkeiten eines<br />

oder aller Angestellten genügend gut ist.<br />

� Anforderung<br />

– Bündelung von mehreren Operationen zu einer Einheit (Transaktion)<br />

– Überprüfung der Integritätsbedingung nur am Beginn / Ende einer Transaktion<br />

� Eine Integritätsbedingung kann nun mit folgenden Schlüsselworten versehen werden:<br />

– not deferrable: Die Integritätsbedingung wird s<strong>of</strong>ort hinter einer Änderung überprüft.<br />

– deferrable: Es besteht jetzt die Möglichkeit der verzögerten Überprüfung.<br />

– deferrable initially deferred: Überprüfung erfolgt am Ende der Transaktion.<br />

– deferrable initially immediate: Überprüfung vor der Änderung.<br />

� Eine mit dem Schlüsselwort deferrable versehene Bedingung mit einem Namen, sagen wir<br />

einfach MeineBedingung, kann noch zur Laufzeit angepasst werden:<br />

– set constraint MeineBedingung deferred<br />

– set constraint MeineBedingung immediate<br />

Seite 155


SQL: Die Sprache relationaler DBMS<br />

4.6.4 Statische Integritätsbedingungen<br />

Attributsbezogene Bedingungen<br />

� Diese Bedingungen beziehen sich auf ein Attribut einer Relation.<br />

– Die Überprüfung dieser Bedingungen findet immer dann statt, wenn das Attribut durch<br />

eine Änderung betr<strong>of</strong>fen ist. Dies sorgt aber nicht dafür, dass auch tatsächlich die<br />

Bedingung stets erfüllt bleibt (wenn z. B. die Bedingung noch von einem anderen Attribut<br />

oder einer anderen Relation abhängt).<br />

� Ausschluss von Nullwerten<br />

create table Personal (pnr int primary key, PName char(20) not null, …)<br />

– Wert des entsprechenden Attributs muss bei jedem Tupel vorliegen.<br />

� Check-Bedingungen<br />

– sind beliebig komplexe Bedingungen, die ähnlich zu einer where-Klausel von SQL<br />

angegeben werden können. Dabei kann man sich direkt auf das Attribut beziehen.<br />

– Beispiel:<br />

create table Personal( pnr int primary key, PName char(20)<br />

check(100 > (select count(*) from Personal A where A.PName = PName)),<br />

…<br />

)<br />

Seite 156


Relationsbezogene Bedingungen<br />

SQL: Die Sprache relationaler DBMS<br />

� Einschränkung der Werte, die ein Tupel bzgl. seiner verschiedenen Attribute annehmen darf.<br />

– Diese Bedingungen werden immer dann überprüft, wenn ein Tupel in die Relation<br />

eingefügt wird oder ein bestehendes Tupel sich ändert.<br />

� In SQL kann eine relationsbezogene Bedingung durch die check-Klausel beim Anlegen des<br />

Schemas angegeben werden.<br />

– In der Bedingung kann man sich auf alle Attribut der zugehörigen Relation beziehen.<br />

� Die Deklaration einer solchen Bedingung erfolgt direkt bei der Deklaration der Relation oder<br />

zu einem späteren Zeitpunkt.<br />

Beispiel:<br />

– Stelle sicher, dass die durchschnittliche Fähigkeit nicht schlechter als 3 ist.<br />

alter table PMZuteilung add check(3 < (select avg(Fähigkeit) from PMZuteilung))<br />

Seite 157


SQL: Die Sprache relationaler DBMS<br />

4.6.5 Verwalten von Integritätsbedingungen<br />

� Integritätsbedingungen können in SQL durch Verwendung des Schlüsselworts constraint<br />

implementiert und dabei mit einem Namen versehen werden.<br />

Hinzufügen/Löschen von Integritätsbedingungen<br />

� alter table PMZuteilung<br />

add constraint plus_const check (Fähigkeit < 1)<br />

– Dies ist stets eine Relationen-Bedingung. Ein Hinzufügen von Attribut-Bedingungen ist<br />

nicht möglich.<br />

� alter table Personal<br />

add constraint name_unique unique PName<br />

� alter table drop constraint <br />

– Löschen wird für beliebige Bedingungen unterstützt.<br />

Seite 158


SQL: Die Sprache relationaler DBMS<br />

Datenbankbezogene Bedingungen<br />

� Hierbei handelt sich um die mächtigste Form von Integritätsbedingungen.<br />

create assertion check <br />

– Die Deklaration erfolgt außerhalb einer Deklaration einer Relation.<br />

– Die Überprüfung der Bedingung bei Änderung einer der beteiligten Relationen.<br />

– Leider werden diese Bedingungen nur von wenigen Systemen unterstützt.<br />

� Im Gegensatz zu den vorherigen check-Klauseln gibt es nicht die Möglichkeit sich direkt auf<br />

ein Attribut einer Relation zu beziehen.<br />

Vergleich von verschiedenen Bedingungen<br />

Typ Ort der Deklaration<br />

Auslösen der<br />

Überprüfung<br />

Attributsbezogene Attribut Einfügen in die Relation<br />

Bedingung<br />

Ändern des Attributs<br />

Relationsbezogene Relationenschema Einfügen in die Relation<br />

Bedingung<br />

Ändern eines Tupels<br />

Datenbankbezogene Datenbankschema Änderung einer der<br />

Bedingung<br />

beteiligten Relationen<br />

Unteranfragen<br />

Nein<br />

Nein<br />

Ja<br />

Seite 159


Trigger-Konzept<br />

SQL: Die Sprache relationaler DBMS<br />

� Zusätzlich können komplexe Integritätsbedingungen auch über so genannte Trigger<br />

spezifiziert werden.<br />

– Trigger werden bereits seit langem von verschiedenen Herstellern angeboten, wobei diese<br />

erst mit SQL3 standardisiert wurden.<br />

– Im Gegensatz zu Assertion können mit einem Tigger auch dynamische<br />

Integritätsbedingungen definiert werden.<br />

� Da das Trigger-Konzept mit einer prozeduralen Erweiterung (PL/SQL) Hand in Hand geht,<br />

verschieben wir eine detaillierte Diskussion auf ein späteres Kapitel.<br />

Seite 160


Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

5. Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

� Wie sieht ein gutes konzeptionelles Schema der Datenbank aus?<br />

� Wie kann die Güte eines Datenbankschemas beurteilt werden?<br />

� Beispiel:<br />

– erstes Schema:<br />

Kunde(KName, KAdr, Kto)<br />

Auftrag(KName, Ware, Menge)<br />

LieferantW(LName, LAdr, Ware, Preis)<br />

– alternatives Schema:<br />

KundenAdr(KName, KAdr)<br />

KundenKto(KName, Kto)<br />

Auftrag(KName, Ware, Menge)<br />

Lieferant(LName, LAdr)<br />

Angebot(LName, Ware, Preis)<br />

Seite 162


Beispiel: LieferantW (LName, LAdr, Ware, Preis)<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

1. Redundanz:<br />

Für jede Ware wird die Adresse des Lieferanten gespeichert.<br />

2. Änderungs-Anomalien (mögliche Inkonsistenzen):<br />

Man kann die Adresse eines Lieferanten in einem seiner Tupel ändern, in einem anderen<br />

jedoch unverändert lassen.<br />

3. Einfüge-Anomalien:<br />

Man kann keine Lieferantenadresse ohne eine Ware einfügen.<br />

4. Entfernungs-Anomalien:<br />

Beim Löschen der letzten Ware geht auch die Lieferantenadresse verloren.<br />

Verbesserung (?):<br />

Lieferant(LName, LAdr)<br />

Angebot(LName, Ware, Preis)<br />

Vorteil:<br />

� Keine Redundanz und keine Anomalien und somit niedrige Kosten bei Änderungen der Daten<br />

Nachteil:<br />

� Bei Anfragen sind zusätzliche Joinoperationen erforderlich und somit höhere Anfragekosten<br />

Finde die Adresse der Lieferanten, die eine Ware liefern können.<br />

Seite 163


Verbesserung ?<br />

Lieferant(LName, LAdr,Ware)<br />

Angebot(Ware, Preis)<br />

vorher:<br />

nachher:<br />

Zusammenfügen durch Join ergibt:<br />

LieferantW LName LAdr Ware Preis<br />

Michl München Milch 1,10<br />

Kohl Frankfurt Milch 1,30<br />

Keller Stuttgart Mehl 2,30<br />

Lieferant LName LAdr Ware<br />

Michl München Milch<br />

Kohl Frankfurt Milch<br />

Keller Stuttgart Mehl<br />

LieferantW LName LAdr Ware Preis<br />

Michl München Milch 1,10<br />

Kohl Frankfurt Milch 1,30<br />

Michl München Milch 1,30<br />

Kohl Frankfurt Milch 1,10<br />

Keller Stuttgart Mehl 2,30<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

Angebot Ware Preis<br />

Milch 1,10<br />

Milch 1,30<br />

Mehl 2,30<br />

Seite 164


Entwurfsziele<br />

� Vermeidung von Redundanzen und Anomalien<br />

� Vermeidung der Probleme bei der Informationsrepräsentation<br />

� Vermeidung des Informationsverlusts<br />

� evtl. Einbeziehung von Effizienzüberlegungen<br />

Grundlage:<br />

– DB-Schema + “funktionale Abhängigkeiten” (Definition folgt)<br />

Vorgehen:<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

– Zerlegen des gegebenen Datenbank-Schemas in ein äquivalentes Schema ohne<br />

Redundanz und Anomalien (“Normalisierung”).<br />

Seite 165


Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

5.1 Funktionale Abhängigkeiten<br />

� statische Integritätsbedingungen:<br />

– Bedingungen an die zugelassenen Ausprägungen des Datenbankschemas<br />

� Funktionale Abhängigkeiten (FDs) = spezielle Integritätsbedingungen<br />

– FD steht für “functional dependency”<br />

� im Folgenden: R bezeichnet eine Relation, <strong>RS</strong>R das Schema und IR die Instanz<br />

Def. (funktionale Abhängigkeit):<br />

Sei R eine Relation und A sowie B Teilmengen des Relationenschemas <strong>RS</strong>R ( A�B�<strong>RS</strong>R). B ist von<br />

A funktional abhängig oder A bestimmt B funktional, geschrieben A�B, gdw. zu jedem Wert in<br />

A genau ein Wert in B gehört:<br />

A�B��IR�t1�t2�IR : t1�A� = t2�A��t1�B� =<br />

t2�B� � Beachte: Funktionale Abhängigkeit ist abhängig von der Semantik des Schemas, nicht von der<br />

Instanz einer Relation!<br />

Seite 166


Beispiel:<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

� Lieferant(LName, LAdr, Ware, Preis)<br />

� Funktionale Abhängigkeiten:<br />

1. {LName} � {LAdr} (ein Lieferantenname bestimmt eindeutig seine Adresse)<br />

2. {LName, Ware} � {Preis}<br />

(der Schlüssel {LName, Ware} bestimmt eindeutig den Preis)<br />

3. {LName} � {LName} (trivial)<br />

4. {LName, Ware} � {Ware} (trivial)<br />

5. {LName, Ware} � {LAdr} (partiell)<br />

Eine Abhängigkeit A�B ist trivial, wenn gilt: B�A Def. (voll, partiell, transitiv):<br />

Eine Abhängigkeit A�B heißt voll, wenn es keine echte Teilmenge C�A gibt, so dass gilt:<br />

C�B. Gibt es eine solche Teilmenge, dann heißt A�B partielle Abhängigkeit.<br />

Seien A und B Attributsmengen aus <strong>RS</strong> ( A�B�<strong>RS</strong>) und gelte A�B und A � B.<br />

Sei X�<strong>RS</strong> ein<br />

Attribut mit X�A�B und gelte B�X. Dann ist X transitiv abhängig von A: A �<br />

X<br />

Seite 167


Berechnung von FDs<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

� Wunsch:<br />

Zu einer gegebenen Menge F von FDs sollen alle gültigen FDs berechnet werden.<br />

� F + ist die Menge aller FDs, die aus den funktionalen Abhängigkeiten in F ableitbar sind. F +<br />

wird auch als Hülle von F bezeichnet.<br />

� Seien <strong>RS</strong> ein Relationenschema, F eine Menge von FDs und ABC � � � <strong>RS</strong>.<br />

Zur Berechnung von F + werden folgende Regeln genutzt (Armstrong Axiome):<br />

– Reflexivität: Sei B�A. Dann gilt stets A � B (Sonderfall: A�A) – Verstärkung: Falls A�B gilt, dann gilt auch A�C�B�C. – Transitivität: Falls A � B und B � C,<br />

dann gilt auch A�C � Es kann gezeigt werden, dass die Regeln korrekt und vollständig sind.<br />

– abgeleitete Regeln sind für alle Relationen des Schemas gültig<br />

– alle gültigen FDs in F + sind mit Hilfe dieser Regeln auch herleitbar<br />

Seite 168


Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

� Trotz dieser Eigenschaften der Amstrong-Axiome ist es komfortabler, noch folgende Regeln<br />

zu benutzen:<br />

– Vereinigungsregel:<br />

Falls A�B und A � C gilt, dann gilt auch A�B�C – Dekompositionsregel:<br />

Falls A�B�C gilt, dann gilt auch A�B und A�C – Pseudotransivität:<br />

Falls A�B und B�C�Dgilt, dann gilt auch A�C�D � Beispiel:<br />

– Lieferanten-Relationen Lieferant(LName, LAdr, Ware, Preis)<br />

– FDs 1-4 seien gültig (siehe oben)<br />

– zu zeigen: FD 5 {LName, Ware} � {LAdr} ist ebenfalls erfüllt.<br />

Es gilt {LName} � {LAdr}.<br />

Auf Grund des 2-ten Amstrong-Axiom gilt auch:<br />

{LName, Ware} �<br />

{LAdr, Ware}<br />

Wegen der Dekompositionsregel ergibt sich damit FD 5.<br />

Seite 169


Membership-Problem<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

� Fragestellung:<br />

Sei F eine Menge von FDs und A�B eine funktionale Abhängigkeit. Gilt A�B F ?<br />

+<br />

�<br />

� Explizite Berechnung von F + ist zu aufwendig<br />

� Stattdessen: Berechnung der Hülle A + der Attributmenge A bzgl. der Menge F<br />

– A + besteht aus allen Attributen, die von A funktional bestimmt werden<br />

– Falls B A gilt, dann gilt auch .<br />

+<br />

� A � B F +<br />

�<br />

Algorithmus Hülle(F, A)<br />

Erg = A;<br />

WHILE (Änderungen an Erg)<br />

FOREACH DO<br />

IF ( ) THEN ;<br />

RETURN A + B�C�F B�Erg Erg =<br />

Erg � C<br />

= Erg;<br />

Seite 170


� Definition:<br />

Kanonische Überdeckung<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

Zwei Mengen F und G von FDs einer Relation R sind äquivalent, falls F + = G + gilt.<br />

� Wunsch: Berechne eine möglichst kleine Menge, die zu F äquivalent ist.<br />

– wenig Aufwand beim Testen, ob ein neues Tupel eine FD verletzt.<br />

� Fc wird als kanonische Überdeckung von F bezeichnet, falls folgende Bedingungen erfüllt<br />

sind:<br />

+<br />

– Fc = F +<br />

– Für alle FDs A�B in Fc gibt es keine “überflüssigen” Attribute, d. h.<br />

für alle Attribute X�A gilt �F c<br />

– �A�B����A– �X�� � B��<br />

.<br />

für alle Attribute gilt .<br />

– Jede linke Seite der FDs in Fc kommt nur einmal vor, d. h.<br />

+ F +<br />

�<br />

Y � B �F c<br />

– �A�B���A��B – �Y���� + F +<br />

�<br />

falls A�B und A�C, dann wird in Fc nur die FD A�B�C verwendet.<br />

Seite 171


Berechnung der kanonischen Überdeckung<br />

1. Führe für jede FD A � B � F die Linksreduktion durch:<br />

Überprüfe für alle X�A, ob das Attribut X überflüssig ist, d.h. ob<br />

B � Hülle�FA � – �X�� gilt. Ist dies der Fall, ersetze A�B durch A– �X��B. Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

2. Führe für jede verbliebene FD A�B � F die Rechtsreduktion durch, d. h.<br />

Überprüfe für alle Y�B , ob das Attribut Y überflüssig ist, d. h.<br />

Y � Hülle�F– �A�B� � �A�B– �Y���A� gilt. Ist dies der Fall, dann wird A�B durch A�B– �Y� ersetzt.<br />

3. Entferne die FDs der Form A � � (die im 2-ten Schritt entstanden sind)<br />

4. Ersetze alle FDs der Form A�B1, A�B2, …, A�Bkdurch A�B1� B2 � … � Bk Seite 172


Beispiel:<br />

� Menge F = { A�B, B�C, A � B �<br />

C }<br />

� Schritt 1:<br />

� Schritt 2:<br />

� Schritt 3:<br />

� Schritt 4:<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

Seite 173


Zerlegung einer Relation<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

� Um Anomalien zu beseitigen, wird eine Relation R mit Schema <strong>RS</strong> R in n Relationen R 1 ,…,R n<br />

mit Schemata <strong>RS</strong> R1 , …, <strong>RS</strong> Rn zerlegt.<br />

� Folgende Eigenschaften sollen erfüllt werden:<br />

– Kein Informationsverlust, d.h. die Relation R muss aus den Relationen R1 ,…,Rn wieder<br />

rekonstruierbar sein.<br />

– Alle FDs, die für die Relation R gelten, sollen für R1 ,…,Rn effizient überprüfbar bleiben.<br />

� Informationsverlust (n=2):<br />

Eine Zerlegung der Relation R in R1 und R2 hat keinen Informationsverlust, wenn folgendes<br />

gilt: R = �<strong>RS</strong>1�R���<strong>RS</strong>2�R�. Satz<br />

Sei R eine Relation und FR die Menge der FDs. Eine Zerlegung von R in R1 und R2 hat keinen<br />

Informationsverlust, falls eine der folgenden Bedingungen gilt:<br />

+<br />

– �<strong>RS</strong> � <strong>RS</strong> � <strong>RS</strong> ��F R1 R2 R1 R<br />

–<br />

�<strong>RS</strong> � <strong>RS</strong> � <strong>RS</strong> ��F R1 R2 R2 R<br />

+<br />

Seite 174


Beispiel:<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

� Die Zerlegung der Relation R(LName, LAdr, Ware, Preis) in die Relationen<br />

– Lieferant(LName, LAdr)<br />

– Lieferant(LName, Ware, Preis)<br />

+<br />

ist verlustlos, da LName � LAdr eine FD aus FR ist.<br />

� Über die Zerlegung<br />

– Lieferant(LName, LAdr, Ware)<br />

– Angebot(Ware, Preis)<br />

können wir auf Grund des Satzes keine Aussage treffen, obwohl wir wissen, dass<br />

– Ware bestimmt nicht funktional den Preis<br />

– Ware bestimmt nicht funktional den LName (und damit auch nicht LAdr)<br />

gilt. Der Satz liefert uns nur eine hinreichende, aber keine notwendige Bedingung!<br />

Seite 175


Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

Bewahrung funktionaler Abhängigkeiten<br />

� Wunsch: alle FDs, die für die Relation R gelten, sollen lokal auf den zerlegten Relationen<br />

R 1 ,…,R n überprüfbar sein (Effizienz !).<br />

� Formal kann dies wie folgt ausgedrückt werden:<br />

Dann wird die Zerlegung als hüllentreu bezeichnet.<br />

Beispiel:<br />

+<br />

FR =<br />

�F���F� R1 Rn<br />

+<br />

� Sei die Relation PV(Straße, Ort, BLand, PLZ) gegeben Es sollen folgende Bedingungen<br />

gelten:<br />

– Orte werden durch “Ort” und “BLand” eindeutig charakterisiert.<br />

– Innerhalb einer Straße ändert sich “PLZ” nicht.<br />

– PLZ-Gebiete gehen nicht über Ortsgrenzen, Orte nicht über Bundeslandgrenzen.<br />

� FDs: {PLZ} --> {Ort, BLand} und {Straße, Ort, BLand} --> {PLZ}<br />

� Welche Eigenschaften besitzt die Zerlegung {PLZ, Straße} und {PLZ, Ort, BLand}?<br />

Seite 176


Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

5.2 Die ersten drei Normalformen<br />

� Durch Normalformen wird definiert, was unter einem guten Datenbankdesign zu verstehen ist.<br />

Def. (1. Normalform):<br />

Eine Relation ist in der 1. Normalform (NF), wenn alle Attribute nur atomare Werte, die nicht<br />

weiter zerlegbar sind, enthalten können. Dafür stehen Wertebereiche wie STRING, INTEGER etc.<br />

zur Verfügung. Mengen von Werten oder sonstige Strukturen (z. B.Tupel) sind nicht erlaubt.<br />

Beispiel (für eine Relation in NF2 ):<br />

� Vor- und Nachteile der Algebra für geschachtelte relationale Datenbanken<br />

(NonFirstNormalForm = NF 2 ) sind z.Zt. in der Diskussion<br />

� Beispiel:NF2 für Literatur (BÜCHER, AUTOR, STICHWORT)<br />

BÜCHER AUTOR STICHWORT<br />

B_1 Boyce Normalisierung<br />

Abhängigkeit<br />

B_1 Codd Normalisierung<br />

Abhängigkeit<br />

Seite 177


Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

Def. (prim):Ein Attribut heißt prim, wenn es Teil eines Schlüsselkandidaten ist, sonst nicht prim.<br />

Def. (2. Normalform):<br />

Eine Relation R ist in der 2. Normalform (2NF), wenn jedes Attribut A�<strong>RS</strong>Rentweder prim oder<br />

von jedem Schlüsselkandidat voll funktional abhängig ist.<br />

Beispiel:<br />

� Leistungsnachweis (S#, K#, Titel, DName, Raum#, Note)<br />

� Tupel (s, k, t, d, r, n) bedeutet: Student s hat die Note n erzielt im Kurs mit Nummer k, der den<br />

Titel t trug und im Raum mit Nummer r vom Dozenten d abgehalten wurde.<br />

Folgende Abhängigkeiten bestehen:<br />

1. {S#, K#} � {Note}<br />

2. {K#} � {Titel}<br />

3. {K#} � {DName}<br />

4. {DName} � {Raum#}<br />

5. {K#} � {Raum#}<br />

Note<br />

S#<br />

K#<br />

Titel<br />

DName<br />

Raum#<br />

Seite 178


Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

Die Relation ‘Leistungsnachweis’ ist nicht in 2NF. Folgende Anomalien können auftreten:<br />

• Informationen über einen neuen Kurs sind nur dann verfügbar, wenn bereits ein Student<br />

für diesen Kurs eingetragen ist.<br />

• Dozent ist nur dann in der Datenbank, wenn er/sie einen Kurs hält<br />

• Namensänderung eines Kurses ist sehr aufwendig (1 Update pro Student)<br />

• Falls alle Studenten den Kurs 27 verlassen und die dazugehörigen Tupel gelöscht<br />

werden, verschwinden alle Informationen über den Kurs.<br />

� Transformation in 2NF behebt diese Anomalien:<br />

– Aufspalten der Relation ‘Leistungsnachweis’ in folgende zwei Relationen:<br />

– Schema in 2NF:<br />

Leistungsnachweis (S#, K#, Note)<br />

Kurs (K#, Titel, DName, Raum#)<br />

Bemerkung:<br />

� 2NF kann nur dann verletzt werden, wenn Schlüsselkandidaten zusammengesetzt sind.<br />

� Partielle funktionale Abhängigkeiten nicht-primer Attribute vom Schlüssel werden beseitigt.<br />

� 2NF spielt in der Normalisierungs<strong>the</strong>orie jedoch kaum mehr eine Rolle.<br />

Seite 179


Def. (3. Normalform):<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

Eine Relation R ist in der 3. Normalform (3NF), wenn für alle Abhängigkeiten X�A mit<br />

X�<strong>RS</strong>R�A�<strong>RS</strong>R�A�X gilt:<br />

• X enthält einen Schlüssel von R, oder<br />

• A ist prim.<br />

� Die Relation ‘Kurs’ ist nicht in 3NF, da die Abhängigkeit DName �<br />

Raum#<br />

DName weder Schlüssel noch Raum# prim ist.<br />

Folgende Anomalien können auftreten:<br />

besteht und<br />

– Informationen über Dozenten und Raum sind ohne Zuordnung eines Kurses nicht<br />

verfügbar<br />

– Ändern der Raumnr. eines Dozenten bedingt die Änderung für jeden Kurs<br />

– Falls ein Dozent keinen Kurs gibt, werden alle Informationen über den Dozent<br />

und seinen Raum aus der Datenbank gelöscht.<br />

Schema in 3NF:<br />

Leistungsnachweis (S#, K#, Note)<br />

Kurs (K#, Titel, DName)<br />

Dozent (DName, Raum#)<br />

� Hinweis:Die 3. Normalform beseitigt Abhängigkeiten von Nicht-Schlüssel-Attributen.<br />

Seite 180


5.3 Syn<strong>the</strong>sealgorithmus<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

� Ziel ist die Zerlegung einer Relation R mit funktionalen Abhängigkeiten F in Relationen<br />

R 1 ,…,R n , so dass folgende Bedingungen erfüllt sind:<br />

– kein Informationsverlust,<br />

– Bewahrung der funktionalen Abhängigkeiten,<br />

– Relationen R1 ,…,Rn erfüllen die dritte Normalform.<br />

� Folgender Algorithmus generiert eine solche Zerlegung:<br />

1. Bestimme die kanonische Überdeckung Fc der Menge F.<br />

2. Führe für jede FD A�B�Fcfolgende Anweisungen aus:<br />

– Erzeuge ein Relationenschema <strong>RS</strong>A = A�B und ordne <strong>RS</strong>A die FDs FA =<br />

�C�D � Fc C�D � <strong>RS</strong>A� 3. Falls alle der in Schritt 2 erzeugten Schemata keinen Kandidatenschlüssel der<br />

ursprünglichen Relation R enthalten, so erzeuge zusätzlich eine Relation mit dem Schema<br />

<strong>RS</strong>K = K und FK = �<br />

, wobei K ein Kandidatenschlüssel von R ist.<br />

4. Eliminiere die Schemata R, die in einem anderen Schema enthalten sind.<br />

Seite 181


Beispiel:<br />

� Relationenschema Pr<strong>of</strong>essorenAdr:<br />

PersNr, Raum, Rang, Name, Straße, Ort, BLand, Landesreg., PLZ, Vorwahl<br />

Annahmen:<br />

� Ort ist der Erstwohnsitz des Pr<strong>of</strong>s<br />

� Landesregierung ist die Partei der<br />

Ministerpräsidentin<br />

� Ortsnamen sind eindeutig innerhalb<br />

der Bundesländer<br />

� PLZ ändert sich nicht innerhalb einer<br />

Straße<br />

� Städte und Straßen liegen vollständig<br />

in Bundesländern<br />

� ein Pr<strong>of</strong> hat genau ein Büro (und er<br />

teilt es nicht)<br />

PersNr<br />

Raum<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

Rang<br />

Name<br />

Straße<br />

Ort<br />

BLand<br />

Landesregierung<br />

PLZ<br />

Vorwahl<br />

Seite 182


1-ter Schritt: Berechnung einer kanonischen Überdeckung<br />

� FD1 {PersNr} � {Raum, Name, Rang, Straße, Ort, BLand}<br />

� FD2 {Raum} � {PersNr}<br />

� FD3 {Sraße, Ort, Bland} � {PLZ}<br />

� FD4 {Ort, BLand} � {Vorwahl}<br />

� FD5 {BLand} � {Landesregierung}<br />

� FD6 {PLZ} �<br />

{Ort, BLand}<br />

2-ter Schritt:<br />

� aus FD 1 ergibt sich:<br />

– {PersNr, Name, Rang, Raum, Straße, Ort, Bland}<br />

– FD1 und FD2 werden zugeordnet<br />

� aus FD 3 ergibt sich:<br />

– {Straße, Ort, Bland, PLZ}<br />

– FD3 und FD6 werden zugeordnet<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

Seite 183


� aus FD 4 ergib sich:<br />

– {Ort, BLand, Vorwahl}<br />

– FD4 wird zugeordnet<br />

� aus FD 5 ergibt sich:<br />

– {BLand, Landesregierung}<br />

– FD5 wird zugeordnet<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

Schritt 3:<br />

� {PersNr} ist Kandidatenschlüssel des ursprünglichen Schemas und befindet sich in einem<br />

Relationenschema.<br />

Schritt 4:<br />

� ist schon im Schritt 2 passiert<br />

Seite 184


5.4 Boyce-Codd Normalform<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

Def. (Boyce/Codd-NF):Eine Relation R ist in Boyce/Codd-Normalform (BCNF), wenn für alle<br />

Abhängigkeiten X�A mit X�<strong>RS</strong>R�A � <strong>RS</strong>R�A�X gilt:<br />

• X enthält einen Schlüssel von R<br />

� Die Boyce/Codd-Normalform beseitigt Abhängigkeiten unter Attributen, die prim sind.<br />

Beispiel: Autoverzeichnis (Hersteller, HerstellerNr, ModellNr)<br />

� Folgende Abhängigkeiten bestehen:<br />

– Hersteller � HerstellerNr(1:1-Beziehung zwischen Hersteller und HerstellerNr)<br />

– HerstellerNr �<br />

Hersteller(s.o.)<br />

� Beispiel ist in 3NF (alle Attribute sind prim), aber nicht in BCNF<br />

� Folgende Anomalien können auftreten:<br />

– Einfügen des selben Herstellers mit verschiedenen Herstellernr. ist möglich<br />

– 1:1-Beziehung von Hersteller und HerstellerNr. ist an die ModellNr gekoppelt<br />

� Sei R eine Relation und FDR die zugehörige Menge funktionaler Abhängigkeiten. Dann gilt:<br />

Es gibt eine Zerlegung von R in Relationen R1 ,…,Rn , so dass<br />

– die Zerlegung verlustlos ist und,<br />

Seite 185


– R i die Boyce-Codd Normalform erfüllen.<br />

Schlechte Nachrichten:<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

� Es kann nicht immer eine abhängigkeitsbewahrende Zerlegung gefunden werden.<br />

Seite 186


Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

5.5 Mehrwertige Abhängigkeiten<br />

� Verallgemeinerung funktionaler Abhängigkeiten<br />

� Beispiel: RelationBuch mit Schema {ISBN, Autor, Stichwort}<br />

ISBN<br />

AUTOR STICHWORT<br />

– ein Buch kann mehrere Autoren besitzen<br />

– mehrere Stichwörter verweisen auf das Buch<br />

– AUTOR bzw. STICHWORT sind mehrwertig abhängig von ISBN<br />

Def. (mehrwertig abhängig):<br />

Sei R eine Relation und A� B� C�<strong>RS</strong>R<br />

mit <strong>RS</strong>R = A� B �C.<br />

Dann ist C mehrwertig<br />

abhängig von A, A »<br />

C , wenn für alle Instanzen IR gilt: Für jedes Paar von Tupel t1 und t2<br />

mit t1[A] = t2[A] existieren zwei Tupel t3 und t4 mit t3[A] = t4[A] = t1[A] und mit folgenden<br />

Eigenschaften:<br />

t3[B] = t1[B] t3[C] = t2[C]<br />

t4[B] = t2[B] t4[C] = t1[C]<br />

Es wird die Kurzschreibweise MVD (multi-value dependency) für eine mehrwertige<br />

Abhängigkeit benutzt.<br />

Seite 187


Beispiel:<br />

� Buch (ISBN, AUTOR, STICHWORT)<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

� Buch besitzt nicht nur zwei Autoren, sondern es existieren auch mindestens zwei Stichworte<br />

� Zerlegen der Relation Buch in zwei Relationen R1 und R2 – <strong>RS</strong> R1 = {ISBN, Autor}<br />

– <strong>RS</strong> R2 = {ISBN, Stichwort}<br />

ISBN AUTOR STICHWORT<br />

I-1 Boyce Normalisierung<br />

I-1 Boyce Abhängigkeit<br />

I-1 Codd Normalisierung<br />

I-1 Codd Abhängigkeit<br />

– Es gilt sogar: Die Zerlegung ist verlustfrei!<br />

Satz<br />

Sei R eine Relation und MR die Menge der MVDs. Eine Zerlegung von R in R1 und R2 hat keinen<br />

Informationsverlust, genau dann falls mindestens eine der folgenden Bedingungen gilt:<br />

+<br />

+<br />

�<strong>RS</strong> � <strong>RS</strong> » <strong>RS</strong> ��Foder R1 R2 R1 R<br />

�<strong>RS</strong> � <strong>RS</strong> » <strong>RS</strong> � �<br />

F R1 R2 R2 R<br />

Seite 188


Vierte Normalform<br />

� ist eine Verstärkung der Boyce-Codd Normalform<br />

� Vermeidung der durch mehrwertige Abhängigkeiten verursachten Redundanz<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

Sei R eine Relation und A�C�<strong>RS</strong>R. Eine mehrwertige Abhängigkeit A<br />

der folgenden Bedingungen gilt:<br />

» C ist trivial, falls eine<br />

1. C�A 2.<br />

C = <strong>RS</strong>R– A<br />

Definition (4NF):<br />

Sei R eine Relation und MR die zugehörige Menge mehrwertiger Abhängigkeiten. R ist in vierter<br />

Normalform (4NF), wenn für jede nicht-triviale mehrwertige Abhängigkeit A » C�MRfolgende<br />

Bedingung gilt: A enthält einen Schlüssel von R.<br />

Seite 189


Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

5.6 Grenzen der Normalisierung<br />

� Auf Grund der Einhaltung von Normalformen existieren Relationen mit “wenigen” Attributen<br />

– Vorteil: Anomalien sind beseitigt, geringe Redundanz<br />

– Nachteil: “ineffiziente” Anfragebearbeitung<br />

Beispiel:<br />

� Gesucht sind Namen und Adressen aller Lieferanten, die ‘Mehl’ liefern.<br />

– Schema: Liefert(LName, LAdr, Ware, Preis)<br />

�LName� LAdr �Ware = Mehl<br />

� �Liefert�� – alternatives Schema:<br />

Lieferant(LName, LAdr)(Schema in 2NF)<br />

Angebot(L Name, Ware, Preis)<br />

�LName� LAdr��Ware<br />

= Mehl�Lieferant<br />

Angebot��<br />

Seite 190


Bisher:<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

5.6.1 Nicht-Standard Anwendungen<br />

� Beispiele aus dem betriebswirtschaftlich/administrativen Bereich Handel, Banken,<br />

Versicherungen, etc., d.h. Standard-Datenbanken und -systeme<br />

� kleine Datenobjekte exakt festgelegter Struktur<br />

� meist einfache Integritätsbedingungen<br />

� viele, kurze Transaktionen auf den Datenbanken (z.B. Buchungen)<br />

Jetzt:<br />

� Betrachtung sog. “Nicht-Standard-Datenbanksysteme” (NDBS)<br />

- CAD / CAM / CIM<br />

- Geographie und Kartographie<br />

- Medizin und Biologie<br />

� komplexe, unterschiedlich strukturierte geometrische Objekte<br />

� <strong>of</strong>t komplexe Integritätsbedingungen (z.B. aus der Geographie)<br />

� häufig sehr lange Operationen (Transaktionen) auf wenigen Objekten (z.B. CAD)<br />

Seite 191


F 1<br />

F 2<br />

F 3<br />

F 4<br />

Beispiel aus der Geographie<br />

F 6<br />

F 5<br />

F 7<br />

Parzellen<br />

FNr KNr<br />

F 1<br />

F 1<br />

F 1<br />

F 1<br />

F 4<br />

F 4<br />

F 4<br />

F 4<br />

F 4<br />

F 4<br />

F 7<br />

F 7<br />

F 7<br />

F 7<br />

K 1<br />

K 2<br />

K 3<br />

K 4<br />

K 2<br />

K 5<br />

K 6<br />

K 7<br />

K 8<br />

K 9<br />

K 7<br />

K 10<br />

K 11<br />

K 12<br />

Kanten<br />

KNr PNr 1 PNr 2<br />

K 1<br />

K 2<br />

K 3<br />

K 4<br />

K 5<br />

K 6<br />

K 7<br />

K 8<br />

K 9<br />

K 10<br />

K 11<br />

K 12<br />

P 1<br />

P 2<br />

P 3<br />

P 4<br />

P 2<br />

P 5<br />

P 6<br />

P 7<br />

P 8<br />

P 6<br />

P 9<br />

P 10<br />

P 2<br />

P 3<br />

P 4<br />

P 1<br />

P 5<br />

P 6<br />

P 7<br />

P 8<br />

P 3<br />

P 9<br />

P 10<br />

P 7<br />

Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

PNr<br />

P 1<br />

P 2<br />

P 3<br />

P 4<br />

P 5<br />

P 6<br />

P 7<br />

P 8<br />

P 9<br />

P 10<br />

Punkte<br />

X-Koord. Y-Koord<br />

X P1<br />

X P2<br />

X P3<br />

X P4<br />

X P5<br />

X P6<br />

X P7<br />

X P8<br />

X P9<br />

X P10<br />

Y P1<br />

Y P2<br />

Y P3<br />

Y P4<br />

Y P5<br />

Y P6<br />

Y P7<br />

Y P8<br />

Y P9<br />

Y P10<br />

Seite 192


Entwurfs<strong>the</strong>orie relationaler Datenbanken<br />

� redundanzfreie Repräsentation der Parzellen erfordert die Verteilung der Informationen auf<br />

drei Relationen: ‘Parzellen’, ‘Kanten’ und ‘Punkte’.<br />

� Anfragen auf den Parzellen müssen die erforderlichen Informationen zunächst<br />

zusammengesetzten:<br />

– Beispiel: Gesucht sind alle Eckpunkte der Parzelle mit Flurnr. 2.<br />

select Punkte.PNr, X-Koord, Y-Koord<br />

from Parzellen, Kanten, Punkte<br />

where FNr = “2” and<br />

Parzellen.KNr = Kanten.KNr and<br />

(Kanten.PNr1 = Punkte.PNr<br />

Kanten.PNr2 = Punkte.PNr)<br />

or<br />

� einfache Anfrage erfordert mehrere Joins<br />

� Ursache: Datenmodellierung und Normalisierung der Relationen<br />

� bessere Datenmodellierung für komplex (speziell geometrische) Objekte<br />

Seite 193


6. Transaktionskonzepte und<br />

Fehlerbehandlung<br />

Transaktionskonzepte und Fehlerbehandlung<br />

� Mehrbenutzerbetrieb:<br />

– DBS bedient gleichzeitig mehrere Benutzer<br />

– Benutzer arbeiten zwar unabhängig voneinander, können aber die gleiche Relation oder<br />

sogar den gleichen Datensatz bearbeiten!<br />

� Aktivität eines Benutzers:<br />

– sequentieller Prozess<br />

� Aktivitäten mehrerer Benutzer:<br />

– variable Menge von ineinander verzahnt ablaufender Prozesse<br />

– gemeinsame Nutzung der Datenbasis<br />

Benutzer Z<br />

Benutzer X<br />

DBMS<br />

Benutzer V<br />

JDBC<br />

ESQL<br />

DB<br />

SQL<br />

SQL<br />

Benutzer Y<br />

Seite 194


Transaktionskonzepte und Fehlerbehandlung<br />

Anwendung eines DBS: Kontoverwaltung<br />

� Ein Benutzer möchte eine Buchung von einem Konto A auf ein Konto B vornehmen können.<br />

� Folgende Anforderungen ergeben sich dabei:<br />

– Eine Buchung sollte nicht teilweise durchgeführt werden.<br />

– Alle Konsistenzbedingungen sollen nach einer Buchung gewahrt bleiben:<br />

z. B. Kontostände dürfen nicht unter 10000,- fallen<br />

– Gleichzeitig ablaufende Buchungen dürfen keinen Einfluss haben auf das Ergebnis dieser<br />

Buchung.<br />

– Eine erfolgreiche Buchung ist auch tatsächlich in der Datenbank wirksam geworden.<br />

� Datenbanksystem<br />

– Mehrere Elementaroperationen werden miteinander zu einer Einheit verschmolzen. Der<br />

Ablauf dieser Einheit wird eine Transaktion genannt.<br />

– Es werden neue Operationen zur Ablaufsteuerung von Transaktionen benötigt.<br />

Seite 195


Operationen<br />

6.1 Transaktionen<br />

Transaktionskonzepte und Fehlerbehandlung<br />

� Elementaroperationen, die sich auf die Datenbasis beziehen<br />

– Lesen des Werts eines Objekts A in eine Programmvariable a:<br />

read(A,a) bzw. r(A)<br />

– Zuweisung eines Werts einer Programmvariable a an ein Objekt A der Datenbank<br />

write(A, a) bzw. w(A)<br />

� Elementaroperationen, die keine Auswirkung auf die Datenbasis haben.<br />

� Ablaufsteuerung<br />

Anfang einer Transaktion: BOT<br />

– Oft wird nach einem Beenden einer Transaktion die nächste Transaktion implizit bereits<br />

geöffnet.<br />

Ende der Transaktion: commit<br />

– Alle in der Transaktion erzeugten Änderungen der Datenbasis werden festgeschrieben.<br />

Abbruch einer Transaktion: abort<br />

– Alle in der Transaktion vorgenommen Änderungen der Datenbasis werden unwirksam.<br />

Seite 196


Transaktionskonzepte und Fehlerbehandlung<br />

Eigenschaften von Transaktionen<br />

� Eine Transaktion (TA) ist eine Folge von Elementaroperationen. Eine TA erfüllt die ACID-<br />

Bedingungen:<br />

A: TA ist die kleinste, atomare Ausführungseinheit.<br />

– Entweder alle durch einen TA vorgenommenen Änderungen werden in der Datenbasis<br />

wirksam oder gar keine.<br />

C: Eine TA überführt einen konsistenten Datenbankzustand in einen anderen konsistenten<br />

Datenbankzustand.<br />

– Innerhalb einer TA sind Inkonsistenzen erlaubt.<br />

I: Eine TA ist gegenüber anderen TAs isoliert, d. h. das Ergebnis einer TA kann nicht direkt<br />

durch eine andere TA beeinflusst werden.<br />

– Jede TA wird logisch so ausgeführt, als gäbe es keine andere TA.<br />

D:Ist eine TA einmal erfolgreich abgeschlossen, dann bleibt ihre Wirkung auf die Datenbasis<br />

dauerhaft erhalten.<br />

– Dies gilt auch im Fall eines Systemfehlers (Verlust des Hauptspeichers).<br />

Seite 197


Tm Tm+1 T n<br />

Transaktionsmanagement<br />

TA-Manager<br />

verzahnter<br />

Ablauf der TAs<br />

� Synchronisation der TAs<br />

– Isolation<br />

� Einschränkung bei den verzahnten Abläufen<br />

� Zurücksetzen einer oder mehrerer TAs<br />

– Atomarität<br />

– Dauerhaftigkeit<br />

�<br />

Einschränkung bei den verzahnten Abläufen<br />

Transaktionskonzepte und Fehlerbehandlung<br />

Seite 198


Notation<br />

� Transaktionen: T 1 , T 2 , …, T n<br />

� Transaktion T j setzt sich aus folgenden Elementaroperationen zusammen:<br />

1. Leseoperation: r j (A)<br />

2. Schreiboperation: w j (A)<br />

3. Abbruch: a j<br />

Transaktionskonzepte und Fehlerbehandlung<br />

4. Commit: c j<br />

5. weitere Operationen, die aber auf die Datenbank keine Auswirkung haben.<br />

� Eine Transaktion T j wird durch einen Aufruf von a j oder c j beendet:<br />

es gibt keine weitere Operation von T j , die danach ausgeführt wird.<br />

� Einzelne Operationen (r j , w j , a j , und c j ) werden sequentiell nacheinander ausgeführt:<br />

– Für einen Ablauf einer TA Tj gibt es eine Ordnungsrelation < j , welche die sequentielle<br />

Ordnung der Elementaroperationen ausdrückt:<br />

op1 < j op2 : �<br />

op1 wird vor op2 ausgeführt.<br />

Seite 199


Ausführungsplan (Historie)<br />

Definition (Ausführungsplan, Historie):<br />

Transaktionskonzepte und Fehlerbehandlung<br />

Seien T 1 ,…,T n Transaktionen. Dann wird eine Folge H aller Operationen der TAs T 1 ,…,T n ein<br />

Ausführungsplan genannt, falls folgende Bedingungen erfüllt sind:<br />

– Es gibt nur Elementaroperationen vom Typ r j , w j , a j , c j .<br />

– Ordnungsrelationen < j der einzelnen Transaktionsabläufe bleiben bewahrt.<br />

Bemerkungen:<br />

� Durch den Ausführungsplan H ist eine Ordnungsrelation < H definiert.<br />

� Nicht alle Ausführungspläne erzeugen einen konsistenten Datenbankzustand (siehe Beispiele)<br />

� Verzahnter Ablauf der TAs wird <strong>of</strong>t auch als parallele Ausführung bezeichnet.<br />

Seite 200


Transaktion T 1 :<br />

read(A, a);<br />

a := a + 10;<br />

write(A, a);<br />

read(B, b);<br />

b := b-10;<br />

write(B, b);<br />

commit;<br />

Transaktion T 2:<br />

read(B, b);<br />

b := b + 10;<br />

write(B, b);<br />

read(C, c);<br />

c := c-10;<br />

write(C, c);<br />

commit<br />

Zeit<br />

Beispiel<br />

ein Ablauf:<br />

T 1 T 2<br />

read(A, a);<br />

read(B, b);<br />

a:= a + 10;<br />

write(A, a);<br />

b := b + 10;<br />

read(B, b);<br />

write(B, b);<br />

b := b-10;<br />

read(C, c);<br />

write(B, b);<br />

commit;<br />

c := c-10;<br />

write(C, c);<br />

commit;<br />

Transaktionskonzepte und Fehlerbehandlung<br />

Ausführungsplan:<br />

r 1 (A);<br />

r 2 (B);<br />

w 1 (A);<br />

r 1 (B);<br />

w 2 (B);<br />

r 2 (C);<br />

w 1(B);<br />

c 1;<br />

w 2(C);<br />

c 2;<br />

Seite 201


Transaktionskonzepte und Fehlerbehandlung<br />

6.1.1 Synchronisationsprobleme<br />

� Ein Ausführungsplan muss gewisse Kriterien erfüllen, damit die Isolationseigenschaft<br />

garantiert ist. Sonst kann es Probleme geben:<br />

Problem des “lost update”<br />

� Transaktion T 1 und T 2 erhöhen das Gehalt eines Mitarbeiters jeweils um 100,- DM<br />

T1 T2 Ausführungsplan<br />

read(Gehalt, g); r1 (Gehalt);<br />

g := g + 100;<br />

read(Gehalt, h); r2 (Gehalt);<br />

write(Gehalt, g); w1 (Gehalt);<br />

commit;<br />

h := h + 100;<br />

c1 write(Gehalt, h); w2 (Gehalt);<br />

commit; c2 � Konsistenz der DB ist i.a. nicht verletzt<br />

� Resultate der Anfragen sind nicht “<strong>of</strong>fenkundig falsch”<br />

Seite 202


Problem der inkonsistenten Sicht auf die Datenbank<br />

Transaktionskonzepte und Fehlerbehandlung<br />

� A und B seien zwei Kontostände für die A+B=0 gelten soll.<br />

� T1 und T2 sind zwei Transaktionen, wobei T1 ändert und T2 nur vom Konto liest.<br />

T 1<br />

read(A, a);<br />

a := a-1;<br />

write(A, a);<br />

read(A, c);<br />

read(B, d);<br />

commit;<br />

read(B,b);<br />

b := b+1;<br />

write(B,b);<br />

commit;<br />

� Transaktion T2 ließt somit inkonsistente Daten aus der Datenbank, obwohl die Datenbank nach<br />

T1 wieder in einem konsistenten Zustand ist.<br />

T 2<br />

Seite 203


Problem der inkonsistenten Datenbank<br />

� A und B seien im Folgenden zwei Kontostände, die stets A = B erfüllen.<br />

T 1<br />

read(A, a);<br />

a := a + 10;<br />

write(A, a);<br />

read(A, c);<br />

c := c*1.1;<br />

write(A, c);<br />

read(B, b);<br />

b := b*1.1;<br />

write(B, b);<br />

commit;<br />

read(B, d);<br />

d := d +10;<br />

write(B,d);<br />

commit;<br />

Die Datenbank hat dauerhaft einen inkonsistenten Zustand:<br />

Aneu = (A+10)*1.1 � B*1.1+10 = Bneu T 2<br />

Transaktionskonzepte und Fehlerbehandlung<br />

Seite 204


Phantom-Problem:<br />

� Transaktion T1 – liest die Daten aller Angestellten,<br />

– berechnet die Höhe einer möglichen Gehaltserhöhung,<br />

– und erhöht entsprechend das Gehalt der Angestellten.<br />

� Transaktion T2 fügt einen neuen Angestellten ein.<br />

Transaktionskonzepte und Fehlerbehandlung<br />

– Wird T 2 nach Schritt 1 von T 1 ausgeführt, so ist die Kalkulation von T 1 veraltet.<br />

Lösung der Synchronisationsprobleme:<br />

� strikte, sequentielle Ausführung der Transaktionen<br />

– Nachteil: schlechte Systemauslastung, lange Wartezeiten<br />

� Beschränkung der “Parallelität” auf erlaubte Verarbeitungsreihenfolgen<br />

Seite 205


6.1.2 Serialisierung von TAs<br />

Transaktionskonzepte und Fehlerbehandlung<br />

� Sei T* = {T1 ,…,Tn } eine Menge von Transaktionen und H ein dazugehörender<br />

Ausführungsplan. Seien Ti und Tj zwei Transaktionen aus T*, die gemeinsam auf ein<br />

Datenobjekt A zugreifen. Es werden nun folgende vier Fälle unterschieden:<br />

1. ri (A) < H rj (A)<br />

2. r i (A) < H w j (A)<br />

3. w i (A) < H r j (A)<br />

4. w i (A) < H w j (A)<br />

Bemerkungen:<br />

– Nur im 1. Fall sind die Operationen vertauschbar, ohne dass sich das Ergebnis des<br />

Ausführungsplans ändert.<br />

– In allen anderen Fällen ist davon auszugehen, dass ein Vertauschen der<br />

Ausführungsreihenfolge zu einem anderen Ergebnis führt. Man spricht dann auch von<br />

einem Konflikt.<br />

Seite 206


Transaktionskonzepte und Fehlerbehandlung<br />

Äquivalenz von Ausführungsplänen<br />

� Definition:<br />

Sei T* = {T1 ,…,Tn } eine Menge von Transaktionen. Seien H und G zwei dazugehörige<br />

Ausführungspläne. Dann sind H und G äquivalent, falls die Konflikte identisch sind, d.h.<br />

wenn für alle Relationen Ti und Tj und ein beliebiges Datenobjekt A folgende Bedingungen<br />

gelten:<br />

ri (A) < H wj (A) �<br />

ri (A) < G wj (A)<br />

wi (A) < H rj (A) �<br />

wi (A) < G rj (A)<br />

wi (A) < H wj (A) �<br />

wi (A) < G wj (A)<br />

� Durch Vertauschen von zwei benachbarten Operationen, die nicht in Konflikt zueinander<br />

stehen, kann man sich einen äquivalenten Ausführungsplan erzeugen.<br />

� Beispiel:<br />

– zwei Relationen T1 und T2 – Ausführungsplan H = (r1 (A),r2 (C),w1 (A),w2 (C),r1 (B),w1 (B),c1 ,r2 (A),w2 (A),c2 )<br />

– Konflikte:<br />

r 1 (A) < H w 2 (A)<br />

w 1 (A) < H r 2 (A)<br />

Seite 207


Transaktionskonzepte und Fehlerbehandlung<br />

Serialisierbare Ausführungspläne<br />

Definition (Serialisierbarkeit):<br />

Ein Ausführungsplan ist serialisierbar, falls es einen äquivalenten sequentiellen Ausführungsplan<br />

gibt.<br />

Serialisierbarkeitsgraph<br />

� Test auf Serialisierbarkeit eines Ausführungsplans.<br />

– Graph G = (K,U) mit Knotenmenge K und Kantenmenge U�K�K – zu jeder TA gibt es genau einen Knoten<br />

– (T1 ,T2 ) � U g.d.w. es gibt ein Objekt O, so dass op1 (O) < H op2 (O) in Konflikt zueinander<br />

stehen.<br />

Satz:<br />

T 1<br />

Ein Ausführungsplan ist genau dann serialisierbar, falls G zyklenfrei ist.<br />

Beweis: siehe Bernstein, Hadzilacos, Goodman.: Concurrency Control and Recovery in <strong>Database</strong><br />

<strong>Systems</strong>. Addison-Wesley 1987.<br />

T 2<br />

Seite 208


Transaktionskonzepte und Fehlerbehandlung<br />

6.2 Synchronisationsverfahren<br />

� In einem DBS soll stets Serialisierbarkeit garantiert werden.<br />

� Zwei prinzipielle Methoden:<br />

– verifizierende (“optimistische”) Verfahren:<br />

Beobachte ständig die Ausführungspläne (über den Graph G). Falls Serialisierbarkeit<br />

nicht garantiert ist, setze eine TA zurück und starte sie neu.<br />

– präventive Verfahren:<br />

Verhindere nicht-serialisierbare Ausführungspläne.<br />

� Bislang verwendete Verfahren:<br />

– Sperrverfahren<br />

– Zeitstempel- und Mehrversionsverfahren<br />

Seite 209


Sperrverfahren<br />

Transaktionskonzepte und Fehlerbehandlung<br />

� Jede TA sperrt den Teil der DB, auf dem sie arbeiten will.<br />

– Solange gesperrt ist, können keine anderen TAs zugreifen<br />

� Klassifizierung der Sperrverfahren nach<br />

– Sperrobjekten: Datensatz, Datenseite, Relation, Datenbank<br />

Beachte:<br />

je feiner die Sperreinheit, desto mehr Parallelität ist möglich<br />

je feiner die Sperreinheit, desto mehr Verwaltungsaufwand<br />

– Sperrmodi<br />

lock(A) sperrt das Datenobjekt A<br />

unlock(A) gibt die Sperre wieder frei<br />

– Sperrprotokoll<br />

Anforderung: Gewährleistung der Serialisierbarkeit<br />

Seite 210


Transaktionskonzepte und Fehlerbehandlung<br />

Zwei-Phasen Sperrprotokoll (2PL)<br />

� 2-Phasen-Sperrprotokoll:<br />

Für jede TA darf nach dem ersten unlock kein lock mehr angefordert werden.<br />

Eigenschaften:<br />

#Sperren<br />

Sperren<br />

Verarbeitung<br />

Freigabe<br />

� Bevor auf ein Objekt A zugegriffen wird, muss es mit einem lock gesperrt werden.<br />

Insbesondere muss eine Sperre direkt vor dem Lesen des Objekts gesetzt werden.<br />

� Das gleiche Objekt darf während einer Transaktion bei einem 2PL nur einmal gesperrt und<br />

freigegeben (unlock) werden.<br />

� Wurde das Objekt verändert, muss es vor der Freigabe (unlock) auch geschrieben werden.<br />

Zeit<br />

Seite 211


Satz:<br />

Beweisskizze:<br />

Transaktionskonzepte und Fehlerbehandlung<br />

Jeder durch ein 2-Phasen Sperrprotokoll erzeugte Ausführungsplan ist serialisierbar.<br />

– Annahme: H ist ein Ausführungsplan mit einem Zyklus T i1 -> … -> T in -> T i1<br />

– Wenn dieser mittels eines 2PL entstanden wäre, dann müsste es Objekte A i1 , …, A in<br />

geben, so dass bzgl. diesen Objekten die Transaktionen in Konflikt stehen. Somit muss<br />

also ein unlock ij (A ij ) vor einem lock ij+1 (A ij ) für j= 1, …,n-1 erfolgt sein und zusätzlich<br />

noch ein lock i1 (A in ) nach dem unlock in (A in ) erfolgen.<br />

Seite 212


� Preclaiming (konservatives 2PL):<br />

#Sperren<br />

Verarbeitung<br />

– keine Verklemmung möglich<br />

– Objekte müssen bei Beginn der TA<br />

bekannt sein<br />

– häufig wird zu viel und zu lange<br />

gesperrt<br />

– Probleme beim Zurücksetzen einer<br />

TA (kaskadierend)<br />

Varianten des 2PL<br />

Freigabe<br />

Zeit<br />

Transaktionskonzepte und Fehlerbehandlung<br />

� EOT-Sperren (striktes 2PL)<br />

#Sperren<br />

Sperren<br />

Verarbeitung<br />

Zeit<br />

– Verklemmungen sind möglich<br />

– Objekte müssen beim Beginn der TA<br />

noch nicht bekannt sein.<br />

– bei Freigabe der Sperren ist<br />

garantiert, dass auf kein Objekt mehr<br />

zugegriffen wird.<br />

– vermeidet Zurücksetzen von bereits<br />

abgeschlossenen TAs<br />

Seite 213


Sperrmodi<br />

Transaktionskonzepte und Fehlerbehandlung<br />

� Das bisherige Vorgehen ist zu restriktiv, da das Sperren von Objekten, die nur gelesen werden,<br />

nicht gesondert behandelt wird.<br />

– Eine Transaktion T2 , die ein Objekt A lesen möchte, muss warten bis die Transaktion T1 ein unlock auf A ausführt (obwohl T1 keine Änderungen an A vornimmt).<br />

RX-Protokoll<br />

� Unterscheidung zwischen zwei Sperrmodi<br />

– S-Sperre: slockT (A)<br />

Das Objekt A darf von der Transaktion T gelesen, aber nicht geschrieben werden. Auf<br />

dem Objekt A sind nun mehrere S-Sperren verschiedener Transaktionen erlaubt (S ist eine<br />

Abkürzung für Shared)<br />

– X-Sperre: xlockT (A)<br />

Die Transaktion T hat nach dem Sperren des Objekts A exklusiven lesenden und<br />

schreibenden Zugriff. Es ist somit nur eine X-Sperre auf einem Objekt A erlaubt (X ist<br />

eine Abkürung für eXclusice)<br />

Seite 214


Transaktionskonzepte und Fehlerbehandlung<br />

Hierarchische Sperrgranulate<br />

� Motivation<br />

– Bisher sind wir davon ausgegangen, dass die Sperren sich auf Objekte der gleichen<br />

Hierarchiestufe beziehen (z. B. Seiten)<br />

– Sperren auf einer höheren Stufe (z. B. Relation) sind dann sinnvoll, wenn bereits viele<br />

Kindobjekte gesperrt wurden. Dadurch kann der Verwaltungsaufwand für die Sperren<br />

erheblich reduziert werden.<br />

� Multiple-granularity Locking<br />

– S: Lesesperre<br />

– X Schreibesperre<br />

– IS Auf Objekten in der darunter liegenden Hierarchie ist eine Lesesperre<br />

beabsichtigt.<br />

– IX Auf Objekten in der darunter liegenden Hierarchie ist eine Schreibesperre<br />

beabsichtigt.<br />

� Erwerb von Sperren<br />

– Top-Down: Bevor ein Objekt gesperrt wird, muss zuerst das Objekt auf der darüber<br />

liegenden Ebene intensional gesperrt sein.<br />

� Zurückgabe von Sperren<br />

Seite 215


– Bottom-up: Feingranulare Sperren werden zuerst zurückgegeben.<br />

� Kompatibilität der Sperrmodi<br />

Beispiel:<br />

Datenbank<br />

Relationen<br />

Seiten<br />

S X IS IX<br />

S x x<br />

X<br />

IS x x x<br />

IX x x<br />

IX 1<br />

X1 S11 S12<br />

Sätze d111 d112 IX 1<br />

D<br />

IS 2<br />

R 1 R2 R 3<br />

Transaktionskonzepte und Fehlerbehandlung<br />

IS 2<br />

S 31<br />

S 2<br />

Seite 216


Transaktionskonzepte und Fehlerbehandlung<br />

6.3 Mehrbenutzersynchronisation in SQL92<br />

� In SQL’92 kann das Korrek<strong>the</strong>itskriterium für die parallele Verarbeitung von Transaktionen<br />

durch Angabe eines Isolationslevel abgesenkt werden.<br />

– Erhöhung des Parallelitätsgrads<br />

– Gefahr einer inkonsistenten Datenbank<br />

� Isolationslevel<br />

– read uncommited<br />

Dies erlaubt lesenden Transaktionen den Zugriff auf noch nicht festgeschriebene Daten<br />

(d.h. Daten können vor dem commit bereits gelesen werden).<br />

– read committed<br />

Daten können nur dann gelesen werden, wenn diese tatsächlich über ein commit<br />

festgeschrieben wurden. Warum garantiert dies noch keine Serialisierbarkeit?<br />

– repeatable reads<br />

Identische Leseoperationen innerhalb der gleichen Transaktion liefern zwar das gleiche<br />

Ergebnis. Das Phantomproblem wird jedoch nicht verhindert.<br />

– serializable<br />

Dies entspricht dem in diesem Kapitel erläuterten Serializierbarkeitsbegriff. Dies ist die<br />

Defaulteinstellung bei einem DBS.<br />

Seite 217


6.4 Fehlerbehandlung<br />

Transaktionskonzepte und Fehlerbehandlung<br />

� Schutz vor Beeinträchtigungen durch Fehler des <strong>Systems</strong> oder eines Benutzers<br />

� nach Systemzusammensturz innerhalb einer TA<br />

– inkonsistenter Zustand der DB<br />

– physische und logische Inkonsistenz<br />

� Recovery-Komponente eines DBS:<br />

– dient zum Wiederherstellen eines korrekten DB-Zustandes<br />

– basiert auf dem TA-Konzept des DBS<br />

Fehlerklassen:<br />

� Transaktionsfehler (z. B. Deadlock, Konsistenzverletzung, Division durch 0)<br />

– Rücksetzen einer oder mehrerer TAs im laufenden Betrieb<br />

� Systemfehler (DBS ist funktionsunfähig, Verlust des Inhalts im Hauptspeicher)<br />

– Rückgängigmachen aller laufenden TAs (Neustart des <strong>Systems</strong>)<br />

� Speicherfehler (Verlust des Plattenspeichers durch “head crash”, selten)<br />

– Rekonstruieren der Datenbank<br />

Seite 218


Transaktionskonzepte und Fehlerbehandlung<br />

Lesen und Schreiben von Datensätzen<br />

AWP 1<br />

AWP 2<br />

A neu<br />

B<br />

Datenbank-Puffer<br />

externe Datenbank<br />

� Datensätze werden in Seiten (Blöcken) auf dem Externspeicher abgelegt.<br />

– Eine Seite ist die kleinste Transfereinheit zwischen Extern- und Hauptspeicher.<br />

� Ein DBS besitzt einen Puffer, in dem Datensätze (und Datenseiten) für die AWPs bereitgestellt<br />

werden.<br />

� Zu jeder Seite im Puffer gibt es genau eine Seite in der externen DB<br />

– Seite in der externen DB ist aber ggf. veraltet.<br />

– Schreiben einer Seite in die DB zerstört den alten Zustand.<br />

A alt<br />

B<br />

Hauptspeicher Externspeicher<br />

Seite 219


Interner Ablauf einer Lese/Schreiboperation<br />

Transaktionskonzepte und Fehlerbehandlung<br />

1. Lies die Seite vom Externspeicher in den Puffer (wenn nicht bereits vorhanden)<br />

2. Fixiere die Seite im Puffer, d.h. die Seite bleibt fest im Hauptspeicher.<br />

3. Setze eine Sperre auf den gewünschten Datensatz.<br />

AWP liest/schreibt den Datensatz und führt weitere Operationen aus.<br />

4. Hebe die Sperre auf.<br />

5. Kennzeichne, dass das AWP die Seite nicht mehr benötigt (Unfix).<br />

Im Fall von Schreiboperationen:<br />

� Datenbank gerät kurzzeitig in einen inkonsistenten Zustand (innerhalb einer TA)<br />

� Modifizierte Seiten im Puffer werden nicht s<strong>of</strong>ort auf den Externspeicher übertragen<br />

– externe DB ist veraltet<br />

– externe DB hat nach dem Ende der TA einen inkonsistenten Zustand.<br />

� Verlust des Hauptspeichers => inkonsistente DB<br />

Ziel:<br />

� DB soll auch bei Verlust des HSP in einem konsistenten Zustand sein.<br />

Seite 220


Freigabe von Seiten<br />

Transaktionskonzepte und Fehlerbehandlung<br />

Varianten beim Lesen/Schreiben<br />

� Pufferverwalter kann diese Seite aus dem Puffer entfernen und (wenn die Seite geändert<br />

wurde) auf den Externspeicher schreiben<br />

� Varianten<br />

– steal: Freigabe vor dem commit einer TA<br />

– no-steal: keine Freigabe vor dem commit der TA.<br />

Schreiben der modifizierten Seiten auf den Externspeicher<br />

� Varianten<br />

– force: Schreiben der Seiten beim commit<br />

– no-force: Schreiben der Seiten zu einem späteren Zeitpunkt<br />

in heutigen DBS:<br />

� no-force und steal<br />

Seite 221


Transaktionskonzepte und Fehlerbehandlung<br />

Protokollierung von Änderungsoperationen<br />

� Mögliche Fälle nach einem commit einer TA (im Fall von steal und no-force):<br />

– externe DB ist in einem inkonsistenten Zustand<br />

– Änderungen sind in der externen DB noch nicht wirksam geworden.<br />

� Protokoll<br />

– REDO-Information:<br />

wenn Änderungen nachvollzogen werden sollen.<br />

– UNDO-Information:<br />

wenn Änderungen rückgängig gemacht werden sollen.<br />

� Eintrag in der Protokolldatei (Log) besteht aus:<br />

– LSN: Log Sequence Number<br />

eindeutige Kennung (monoton wachsend)<br />

– TA_ID: Transaktionskennung<br />

– SID: Seitennummer<br />

– REDO-Information<br />

– UNDO-Information<br />

– P_LSN: Zeiger auf den vorherigen Log-Eintrag der Transaktion TA_ID.<br />

Seite 222


Physisches Logging<br />

Varianten beim Logging<br />

Transaktionskonzepte und Fehlerbehandlung<br />

� Explizite Angabe des neuen Zustands des Objekts (“after image”) und des alten Zustands<br />

(“before image”)<br />

Logisches Logging<br />

� Angabe der Operation (für redo) und der zugehörigen Umkehrfunktion (undo)<br />

Physiologisches Logging<br />

� physisches Logging auf der Seitenebene<br />

� logisches Loggig innerhalb einer Seite<br />

Seite 223


Beispiel:<br />

Transaktionskonzepte und Fehlerbehandlung<br />

Transaktion T1 Transaktion T2 logische Protokolldatei physiologische Protokolldatei<br />

begin-TA <br />

r(A,a1 old )<br />

a1 new = a1 old - 10<br />

begin_TA <br />

r(C,c old )<br />

w(A,a1 new ) <br />

r(B, b old )<br />

b new = b old + 10<br />

c new = c old + 20<br />

w(C,c new ) <br />

w(B, b new ) <br />

commit <br />

r(A,a2 old )<br />

a2 new = a2 old - 20<br />

w(A,a2 new ) <br />

commit <br />

� Unter Verwendung der UNDO- und der REDO-Information ist es also möglich den vorherigen<br />

Zustand der Seite zu rekonstruieren.<br />

Seite 224


Transaktionskonzepte und Fehlerbehandlung<br />

� Bei der logischen Protokollierung ist es aber noch wichtig, den Zustand der betr<strong>of</strong>fenen Seite<br />

zu kennzeichnen:<br />

– LSN der zuletzt auf der Seite wirksamen Schreiboperation wird in der Seite zusätzlich<br />

abgespeichert.<br />

� Zwei Fälle können nun unterschieden werden:<br />

– LSN der Seite < LSN eines Protokolleintrags<br />

– LSN der Seite >= LSN des Protokolleintrags<br />

Seite 225


Transaktionskonzepte und Fehlerbehandlung<br />

Verwaltung der Protokolleinträge<br />

AWP 1<br />

AWP n<br />

abstrakte SQL-Mashine<br />

Schreiben<br />

in den Puffer<br />

DB-<br />

Puffer<br />

Log-<br />

Puffer<br />

Implementierung als Ringpuffer<br />

Datenbank DB-Archiv<br />

Log-Datei Log-Archiv<br />

Schreiben auf<br />

Log-Datei<br />

Seite 226


Transaktionskonzepte und Fehlerbehandlung<br />

Schreiben der Einträge in die Log-Datei<br />

� Folgende Regeln müssen beim Schreiben der Log-Einträge befolgt werden:<br />

– Vor dem commit einer TA müssen alle zugehörigen Protokolleinträge in die Log-Datei<br />

geschrieben werden.<br />

– Vor dem Schreiben einer modifizierten Seite in die (externe) Datenbank müssen alle<br />

zugehörigen Protokolleinträge geschrieben werden.<br />

� Wenn ein Protokolleintrag mit LSN x in die Log-Datei geschrieben wird, so müssen vorher<br />

alle Einträge mit LSN y, y < x, geschrieben worden sein.<br />

� Diese Vorgehensweise nennt man auch Write Ahead Log (WAL)<br />

Seite 227


Transaktionskonzepte und Fehlerbehandlung<br />

6.4.1 Wiederanlauf nach einem Systemfehler<br />

� Ursache: Verlust des Hauptspeichers<br />

� Zwei Arten von TA<br />

– Winner:<br />

Für TAs, die bereits mit commit beendet wurden, müssen die durchgeführten Änderungen<br />

in der DB nachvollzogen werden. Warum ?<br />

– Loser:<br />

Für TAs, die zum Zeitpunkt es Absturzes aktiv waren, aber noch nicht mit commit<br />

beendet wurden, müssen die Änderungen rückgängig gemacht werden.<br />

� Wiederanlauf geschieht in drei Phasen:<br />

– Analyse: Bestimme Winner und Loser<br />

– Wiederholung der Historie (REDO)<br />

– Zurücksetzen der Loser (UNDO)<br />

Analyse<br />

� sequentielles Durchlaufen der Log-Datei vom Anfang bis zum Ende<br />

– TA mit einem Eintrag “begin_TA” und einem Eintrag “commit” sind Winner.<br />

– TA mit einem Eintrag “begin_TA” ohne einem Eintrag “commit” sind Loser.<br />

Seite 228


REDO-Phase<br />

Transaktionskonzepte und Fehlerbehandlung<br />

� Sequentielles Durchlaufen der Einträge in der Log-Datei vom Anfang bis zum Ende<br />

– Lies die zugehörige Seite vom Externspeicher<br />

Falls LSN der Seite < LSN des Eintrags:<br />

(i) Führe REDO-Operation aus.<br />

(ii) Übertrage die LSN des Eintrags in die Seite.<br />

UNDO-Phase<br />

� Sequentielles Durchlaufen der Einträge in der Log-Datei vom Ende bis zum Anfang<br />

– Führe für jede Loser-TA die UNDO-Operation aus.<br />

Zusätzlich:<br />

– Schreiben von Kompensationseinträgen in die Log-Datei<br />

Seite 229


Transaktionskonzepte und Fehlerbehandlung<br />

Fehlerbehandlung beim Wiederanlauf<br />

� “Schicksalsstunden” im Leben einer Datenbank<br />

– Stromausfall: Verlust es Hauptspeichers<br />

– Wiederanlauf des <strong>Systems</strong><br />

– erneuter Stromausfall (bevor der Wiederanlauf beendet wurde)<br />

� Anforderung: Idempotenz der UNDO- und REDO-Operationen<br />

– Ergebnis einer beliebig <strong>of</strong>t ausgeführten UNDO/REDO-Operation entspricht dem<br />

Ergebnis einer einmalig ausgeführten UNDO/REDO-Operation<br />

� Offensichtlich gilt: REDO-Operationen sind idempotent<br />

Idempotenz der UNDO-Operation<br />

� Diese Eigenschaft wird durch Kompensationseinträge in der Protokolldatei sichergestellt.<br />

� Für jede ausgeführte UNDO-Operation wird ein Eintrag erzeugt:<br />

– Dieser besitzt keine UNDO-Information.<br />

– Seine REDO-Information entspricht dabei der (ausgeführten) UNDO-Operation.<br />

– Zusätzlich gibt es noch einen Verweis auf einen Eintrag in der Log-Datei<br />

(UNDO_P_LSN).<br />

Seite 230


Beispiel:<br />

� Transaktionen T 1 und T 2<br />

Log-Datei (vor dem Wiederanlauf)<br />

#1 #2 #3 #4 #5 #6 #7<br />

Log-Datei nach dem Wiederanlauf<br />

� UNDO_P_LSN<br />

– Zeiger auf die nächste auszuführende UNDO-Operation der TA.<br />

Transaktionskonzepte und Fehlerbehandlung<br />

#1 #2 #3 #4 #5 #6 #7 #8 #9 #10<br />

UNDO_P_LSN<br />

NIL<br />

Seite 231


6.4.2 Rücksetzen einer TA<br />

Gründe für das Zurücksetzen einer TA<br />

Transaktionskonzepte und Fehlerbehandlung<br />

� System muss eine oder mehrere TAs zurücksetzen (z. B. wegen einer Verklemmung).<br />

� Benutzer bricht seine TA ab.<br />

Anforderung:<br />

Ablauf<br />

– alle DB-Änderungen der TA müssen zurückgenommen werden<br />

– lokal für eine TA möglich, wenn noch keine Sperren freigegeben wurden<br />

� sequentielles Durchlaufen der Protokolldatei vom Ende bis zum ersten Eintrag der TA, die<br />

zurückgesetzt werden soll:<br />

– Ausführen der UNDO-Operation<br />

– Eintrag eines Kompensationseintrags<br />

– Aufsuchen des nächsten Eintrags (mit P_LSN)<br />

� Sperren der TA müssen zusätzlich beim Rücksetzen freigegeben werden.<br />

Seite 232


6.4.3 Sicherungspunkte<br />

� Nachteil beim Zurücksetzen: Protokolldateien können sehr groß werden!<br />

� Einführung von Sicherungspunkte, so dass idealerweise<br />

– der Wiederanlauf startet am letzten Sicherungspunkt<br />

– und ältere Protokolleinträge gelöscht werden können.<br />

Arten von Sicherungspunkten (savepoints, checkpoints)<br />

Transaktionskonzepte und Fehlerbehandlung<br />

� Transaktionskonsistente Sicherungspunkte<br />

– Überführung des <strong>Systems</strong> in einen Ruhezustand (d.h. keine TA ist mehr aktiv)<br />

– Schreiben aller modifizierten Seiten<br />

– Neuinitialisierung der Protokolldatei<br />

– Starten der wartenden TA<br />

Nachteil:<br />

– Verzögerung der TA<br />

– großer Aufwand beim Schreiben des Pufferinhalts<br />

Seite 233


Transaktionskonzepte und Fehlerbehandlung<br />

Aktionsbasierte Sicherungspunkte<br />

� Dabei ist keine Beruhigung des <strong>Systems</strong> erforderlich. Stattdessen müssen nur die elementaren<br />

Änderungsoperationen abgeschlossen werden.<br />

T5<br />

T4<br />

T3<br />

T2<br />

T1<br />

MIN_LSN<br />

Sicherungspunkt<br />

� Folgende Aktionen werden ausgeführt:<br />

– Schreiben des Log-Puffers und des DB-Puffers (WAL-Prinzip !)<br />

– Berechnen der Liste STA aller zum Zeitpunkt des Sicherungspunktes aktiven TAs<br />

– Berechnen von MIN_LSN = min {LSN | LSN gehört zu einer TA aus S TA }<br />

� Analyse- und REDO-Phase setzt beim Sicherungspunkt auf.<br />

� UNDO-Phase muss aber bis MIN_LSN gehen.<br />

Abbruch<br />

Zeit<br />

Seite 234


Ziel<br />

Unscharfe Sicherungspunkte<br />

Transaktionskonzepte und Fehlerbehandlung<br />

� Reduzierung der Systembelastung durch schrittweises Weitersetzen von Sicherungspunkten<br />

Folgende Datenstrukturen werden nun benötigt<br />

� “schmutzige” Pufferseiten sind miteinander verkettet bzgl. der LSN der zuletzt in der Seite<br />

ablaufenden Änderung.<br />

– Seite am Kopf der Liste besitzt die kleinste LSN (MIN_LSN_DIRTY).<br />

– MIN_LSN_DIRTY ist quasi die LSN des Sicherungspunkts<br />

� Liste STA enthält alle zum Zeitpunkt MIN_LSN_Dirty aktiven TAs<br />

� MIN_LSN ist die kleinste LSN die in TAs aus S TA vorkommt.<br />

Seite 235


6.4.4 Rekonstruktion<br />

Transaktionskonzepte und Fehlerbehandlung<br />

� Rekonstruktion eines korrekten DB-Zustand (mit möglichst wenig Verlust)<br />

� Vorgehensweise:<br />

– DB-Kopie, ein so genannter Dump, wird benötigt zu einem zurückliegenden Zeitpunkt<br />

(sehr teuer, deshalb selten)<br />

– Verwende Dump und wiederhole alle seitdem beendete TAs<br />

� Hierzu werden folgende Daten benötigt:<br />

– “after images” veränderter Objekte (benötigt bis zum letzten Dump)<br />

– entsprechende Protokolldatei wird von vorne nach hinten gelesen<br />

T5<br />

T4<br />

T3<br />

T2<br />

T1<br />

Dump<br />

Abbruch<br />

Zeit<br />

Seite 236


7. Anwendungsprogrammierung<br />

Anwendungsprogrammierung<br />

� Anwendungen werden typischerweise in imperativen Sprachen entwickelt (C, Cobol, Fortran,<br />

Java, C++, C#…)<br />

– reichhaltige Funktionalität bei der “gewöhnlichen” Programmierung<br />

– keine Unterstützung von Persistenz (Datenbankprogrammierung)<br />

– flexibles Datenmodell:<br />

basiert auf der Verarbeitung von einzelnen Datensätzen<br />

� Datenbankanfragesprachen (SQL) sind deskriptiv<br />

– wenig Funktionalität für die “alltägliche” Programmierung:<br />

Einfache Aufgaben wie z. B. die “Berechne den Flächeninhalt eines beliebigen Polygons”<br />

sind in SQL nicht möglich.<br />

– sehr komfortabel für die Datenbankprogrammierung<br />

– restriktives Datenmodell:<br />

im Wesentlichen nur Verarbeitung von Mengen (Relationen)<br />

Frage:<br />

� Wie kann die Programmierung von Datenbankaufgaben mit der von “gewöhnlichen”<br />

Aufgaben verbunden werden (ohne dabei die Vorteile von SQL aufzugeben)?<br />

Seite 237


Evolutionäre Ansätze:<br />

Kopplungsmöglichkeiten<br />

� CALL-Schnittstelle<br />

– Bereitstellung von Biblio<strong>the</strong>ken<br />

� Einbettung mit Vorübersetzer<br />

– statisch: Struktur der SQL-Befehle ist bereits vorgegeben<br />

– dynamisch: beliebige SQL-Befehle<br />

� Spracherweiterungen<br />

– von SQL<br />

– von einer imperativen Programmiersprache (z. B. PASCAL)<br />

� Skriptsprachen<br />

– BASIC-ähnliche Sprachen ohne Typkonzept<br />

– einfache Anbindung an Window- und Graphikumgebung<br />

Anwendungsprogrammierung<br />

Seite 238


Anwendungsprogrammierung<br />

7.1 Prozedurale CALL-Schnittstelle<br />

� basiert auf der Verwendung einer Biblio<strong>the</strong>k<br />

– im Fall von Oracle: Oracle Call Interface (OCI)<br />

– im Fall von SQL Server (ODBC)<br />

– …<br />

Quelldateien<br />

Host-Compiler<br />

Host-Linker<br />

DBMS-Biblio<strong>the</strong>k<br />

AWP DBMS-Server<br />

Datenbank<br />

Seite 239


Anwendungsprogrammierung<br />

Komponenten der CALL-Schnittstelle<br />

� Gemeinsam vom AWP und dem Datenbank-Server genutzte Datenstrukturen:<br />

– zum Aufbau der Kommunikation<br />

– zur Bearbeitung einer Anfrage<br />

� Cursor: Im AWP benutzte Datenstruktur zum Zugriff auf Relationen der DB.<br />

� SQL-Anfragen werden im AWP als String repräsentiert.<br />

– AWP muß einen erheblichen Teil der Typüberprüfung übernehmen.<br />

� Binden der Variablen aus dem AWP an die Datenstrukturen des DBMS-Servers<br />

Ablauf eines AWP:<br />

Aufbau der Verbindung<br />

zum DBMS-Server<br />

Initialisieren<br />

eines Cursors<br />

Parsen eines<br />

SQL-Statements<br />

Binden von Eingabevariablen<br />

an das SQL-Statement<br />

Ausführen eines<br />

Updates (einer Anfrage)<br />

Schließen des<br />

Cursors<br />

Abkoppeln<br />

vom Server<br />

Seite 240


Ausführen einer Anfrage (im Detail):<br />

Abfragen der<br />

Ausgabeparameter<br />

Nachteil bei der Benutzung der CALL-Schnittstelle:<br />

Anwendungsprogrammierung<br />

� komplizierte Programmierung<br />

– Abbildung zwischen den Objekten des AWP und den Objekten der Datenbank<br />

� fehleranfällig<br />

– Typsystem der Programmiersprache und des Datenbanksystems sind unterschiedlich<br />

Vorteile<br />

Binden der Ausgabe<br />

an Variablen des AWP<br />

� hohe Flexibilität<br />

– Generierung und Kompilieren von Anfragen zur Laufzeit des AWP<br />

Setzen des<br />

Cursors<br />

Abbrechen der<br />

Anfrage<br />

Seite 241


7.1.1 JDBC<br />

Anwendungsprogrammierung<br />

� JDBC steht für Java <strong>Database</strong> Connectivity<br />

� Java API für die Programmierung relationaler DBMS<br />

– Anfragen werden vom Java-Anwendungsprogramm als uninterpretierte Zeichenketten an<br />

das DBMS gegeben.<br />

– Resultate werden als Objekte einer Klasse ResultSet vom DBMS an das AWP geliefert.<br />

� JDBC bietet eine einheitliche Schnittstelle für verschiedene DBMS<br />

– ähnlich zu ODBC (Open DataBase Connectivity), aber plattformunabhängig<br />

– JDBC ist unter dem Paket java.sql integraler Bestandteil der Standard API von Java<br />

� Unterstützung des Client-Server Konzepts<br />

– DBMS läuft logisch auf einem anderen Rechner als das AWP<br />

� Unterstützung wichtiger Konzepte<br />

– Verschiedene Typen von Anfragen (statische Anfragen, parametrisierbare Anfragen,<br />

Aufruf von gespeicherten Prozeduren)<br />

– Änderungsoperationen auf Relationen und dem Schema<br />

– Zugriff auf Metadaten<br />

Seite 242


ResultSet<br />

getXXX<br />

Datentypen<br />

Wichtige Klassen bei JDBC<br />

executeQuery<br />

getResults<br />

executeQuery<br />

setXXX<br />

getXXX<br />

Statement<br />

IS-A<br />

PreparedStatement<br />

IS-A<br />

CallableStatement<br />

createStatement<br />

prepareStatement<br />

prepareCall<br />

Anwendungsprogrammierung<br />

Connection<br />

DriverManager<br />

getConnection<br />

� Die Namen in den Rechtecken entsprechen den Namen der verfügbaren Schnittstellen<br />

� Die gerichteten durchgezogenen Kanten zeigen, wie man ein Objekt einer Klasse (auf die eine<br />

Kante gerichtet ist) mit Hilfe der anderen Klasse erzeugt.<br />

Seite 243


Client/Server Kopplung in JDBC<br />

Aufbau einer Verbindung<br />

Anwendungsprogrammierung<br />

� Als erstes muß zunächst die entsprechende Treiberklasse angemeldet werden.<br />

Class.forName("oracle.jdbc.driver.OracleDriver") ;<br />

� Danach wird ein Connection Objekt erzeugt.<br />

Connection con = DriverManager.getConnection ("jdbc:oracle:thin:@venus.ma<strong>the</strong>matik.unimarburg.de:1521:Init_DB",<br />

"scott", "tiger");<br />

– Erste Zeichenkette entspricht einer URL zur Datenbank<br />

– Zweite Zeichenkette ist der Benutzername<br />

– Dritte Zeichenkette ist das Passwort<br />

4 verschiedene Treiberklassen bei JDBC<br />

1. Native API-Treiber<br />

2. JDBC-ODBC Bridge<br />

3. JDBC-Middleware<br />

4. Natives Protokoll<br />

Seite 244


Native API-Treiber<br />

Anwendungsprogrammierung<br />

Spezielle Netzs<strong>of</strong>tware des DBMS wird auf dem Client installiert. Methoden in JDBC werden<br />

nativ auf die Methoden der darunter liegenden Netzs<strong>of</strong>tware abgebildet.<br />

Nachteile<br />

� Installation der Netzs<strong>of</strong>tware auf allen Clients<br />

– keine Unabhängigkeit vom Datenbanksystem<br />

– Keine Nutzung im Internet<br />

Vorteil<br />

� relativ gute Performance<br />

Client Server<br />

JDBC<br />

DBMS-Net<br />

DBMS<br />

Seite 245


Vorteil<br />

JDBC-ODBC Bridge<br />

Anwendungsprogrammierung<br />

ODBC-Treiber und ggf. weitere Datenbank-S<strong>of</strong>tware sind auf dem Client verfügbar. Methoden<br />

von JDBC werden auf die Funktionalität von ODBC abgebildet.<br />

� Unabhängigkeit von speziellen Datenbanksystemen, da ODBC sehr weit verbreitet ist.<br />

Nachteil<br />

Client Server<br />

JDBC<br />

ODBC-Treiber +<br />

Datenbank-S<strong>of</strong>tware<br />

DBMS<br />

� Installation von ODBC + Datenbanktreiber auf allen Clients<br />

– keine Anbindung im Internet<br />

� Anfragen und Ergebnisse müssen über die ODBC-Brücke verschickt werden.<br />

– schlechte Performance<br />

Seite 246


Vorteil<br />

JDBC-Middleware<br />

Anwendungsprogrammierung<br />

Ähnlich zur ersten Lösung, aber die Netzs<strong>of</strong>tware ist durch Nutzung einer Middleware unabhängig<br />

vom spezifischen DBMS.<br />

� Keine Installation von spezieller S<strong>of</strong>tware am Client<br />

– Einfacher (und kleiner) Java-Treiber wird bei Bedarf geladen<br />

� Unabhängigkeit vom DBMS<br />

� Optimierung auf dem Server (wie z. B. Pufferung von Ergebnissen)<br />

Nachteil<br />

Client Server<br />

JDBC<br />

Java-Treiber<br />

DBMS<br />

Middle-Net<br />

� Alle Ergebnisse werden über die Middleware nach außen gegeben.<br />

Seite 247


Natives Protokoll<br />

Anwendungsprogrammierung<br />

Ein speziell in Java implementierte Netzwerkverbindung übermittelt die Anforderungen des<br />

Clients an einen Server. Beim Server wird dann die Anforderung direkt an das DBMS weitergereicht.<br />

Vorteile<br />

� S<strong>of</strong>tware auf dem Client ist in Java geschrieben und kann bei Bedarf geladen werden.<br />

� Direkte Interaktion mit dem DBMS (Vermeidung einer Zwischeninstanz)<br />

– gute Performance<br />

Nachteil<br />

Client Server<br />

JDBC +<br />

Datenbanktreiber<br />

� Für jedes DBMS benötigt man einen eigenen Treiber.<br />

DBMS<br />

Seite 248


Treibermanager<br />

Treibermanagement von JDBC<br />

Anwendungsprogrammierung<br />

� Vermittlungsschicht zwischen Anwendung und dem eigentlichen Datenbanktreiber<br />

� Es gibt nur einen Treibermanager pro Programm<br />

=> nur statische Methoden in der Klasse DriverManager<br />

� Unterstützung folgender Operationen<br />

– Registrieren und Laden von Treibern<br />

– Herstellen einer Verbindung zur Datenbank<br />

– Konfiguration der Verbindung<br />

� Laden eines Treibers<br />

– Explizites Laden im AWP über einen Aufruf der Methode Class.forName<br />

– Über die Systemeigenschaft jdbc.drivers der JVM<br />

java -Djdbc.drivers=foo.bas.Driver:wom.sql.Driver JDBCDemo1<br />

Es wird das Programm JDBCDemo1 gestartet und in der Kommandozeile der<br />

verwendete Treiber mitgeteilt.<br />

Seite 249


Anwendungsprogrammierung<br />

– Beim Laden eines Treibers, registriert der Treiber sich beim Treibermanager (durch<br />

Aufruf der Methode registerDriver der Klasse DriverManager).<br />

Treiber<br />

� Wichtig für die Praxis sind Methoden zum Abgreifen von Daten über die Version des Treibers<br />

und seinen Leistungsumfang.<br />

– Z. B. liefert die Methode jdbcCompliant der Schnittstelle Driver nur dann true, wenn der<br />

Treiber SQL92 Entry Level unterstützt und den JDBC-Test erfolgreich bestanden hat.<br />

Aufbau einer Datenbankverbindung<br />

� erfolgt über den Aufruf einer Methode mit Namen getConnection aus der Klasse<br />

DriverManager.<br />

– Alle diese Methoden erwarten eine URL als Parameter, genauer gesagt eine JDBC-URL.<br />

� Aufbau einer JDBC-URL<br />

jdbc::<br />

Weitere Funktionalität<br />

� Setzen einer maximalen Wartezeit zur Anmeldung am Server<br />

� Protokollierung von Fehlermeldungen<br />

Seite 250


7.1.2 Datenverbindungen bei JDBC<br />

Anwendungsprogrammierung<br />

� Eine Verbindung wird in JDBC durch ein Objekt der Klasse Connection repräsentiert.<br />

– getConnection liefert als Ergebnis ein solches Objekt zurück.<br />

� Unterstützte Funktionalität<br />

– Senden von SQL-Anweisungen an den Datenbankserver<br />

– Steuerung von Transaktionen<br />

– Empfang von Resultaten vom Server<br />

– Abgreifen von Metainformation über die Datenbank<br />

Seite 251


Transaktionen<br />

Anwendungsprogrammierung<br />

� Eine Transaktion ist eine Folge von SQL-Befehlen, die atomar verarbeitet werden.<br />

– Durch den Befehl commit wird die Transaktion abgeschlossen und die Änderungen sind<br />

dann danach garantiert in der Datenbank.<br />

– Durch den Befehl rollback wird die Transaktion wieder zurückgefahren, d. h. alle<br />

bisherigen Operationen in der Transaktion sind unwirksam.<br />

� Eine Transaktion wird implizit mit dem ersten Befehl (nach commit und rollback) gestartet.<br />

� Objektmethoden<br />

– commit() und rollback() sind Methoden mit der bekannten Semantik<br />

– void setAutoCommit(boolean enable)<br />

Ist AutoCommit gesetzt, ist jeder Befehl eine Transaktion. Ansonsten muß die<br />

Transaktion explizit durch commit bzw. rollback abgeschlossen werden.<br />

– Methode setTransactionIsolation erlaubt das Einstellen eines sogenannten<br />

Isolationslevels. (Siehe auch Kapitel Transaktionen)<br />

Seite 252


7.1.3 Anfragen<br />

Anwendungsprogrammierung<br />

� In java.sql wird zwischen drei Anfragetypen unterschieden<br />

– Statement<br />

Einfache Anfragen ohne Parametrisierung<br />

– PreparedStatement<br />

Vorübersetzte Anfrage, die Eingabeparameter unterstützt.<br />

– CallableStatement<br />

Aufruf von gespeicherten Prozeduren, die auf dem DBMS hinterlegt sind.<br />

� Zur Ausführung von allgemeinen SQL-Anfragen stehen folgende execute-Methoden zur<br />

Verfügung:<br />

– ResultSet executeQuery(String sql)<br />

Ausführung einer Anfrage mit SELECT-Klausel, wobei das Ergebnis ein Objekt der<br />

Klasse ResultSet ist.<br />

– int executeUpdate(String sql)<br />

Dadurch können Änderungsoperationen (Einfügen neuer Tupel, Löschen, …) unterstützt<br />

werden. Als Ergebnis wird die Anzahl der involvierten Tupel geliefert.<br />

Weiterhin können auch Schemaänderungen formuliert werden (z. B. create table, …).<br />

Dann ist das Ergebnis stets 0.<br />

Seite 253


Anwendungsprogrammierung<br />

– boolean execute(String sql)<br />

Diese Methode wird dann aufgerufen, wenn es nicht bekannt ist, ob die SQL-Anweisung<br />

eine Anfrage ist (Rückgabewert true) oder eine Änderungsoperation (false). Auch kann<br />

diese Methode verwendet werden, wenn eine Anweisung mehr als ein Resultat besitzt.<br />

Inkompatibilität von SQL-Dialekten<br />

– Ein primäres Ziel von JDBC ist die Unabhängigkeit des AWP vom zugrunde liegenden<br />

DBMS. Leider gibt es eine Vielzahl von Unterschieden bei den verschiedenen SQL-<br />

Dialekten.<br />

Outer-Join in SQL92 Standard<br />

select Emp.name, Proj.name<br />

from Emp left outer join Proj on Emp.pid = Proj.id<br />

Outer-Join in SQL von Oracle<br />

select Emp.name, Proj.name<br />

from Emp, Proj<br />

where Emp.pid = Proj.id(+)<br />

– Zur Überwindung solcher Abhängigkeiten gibt es in JDBC eine Escape-Klausel. Diese<br />

Klausel wird vom Treiber erkannt und dann in den spezifischen Dialekt des DBMS<br />

transformiert. Eine Escape-Klausel besteht aus einem Schlüsselwort und einer Menge von<br />

Parametern.<br />

{ …}<br />

Seite 254


Beispiel: Outer-Join mit Escape-Klausel<br />

Outer-Join mit Escape-Klausel<br />

select Emp.name, Proj.name<br />

from {oj Emp left outer join Proj<br />

on Emp.pid = Proj.id}<br />

Anwendungsprogrammierung<br />

– Der Funktionsumfang von Escape-Klauseln hängt stark vom jeweiligen Treiber ab!<br />

– Ein bekanntes Beispiel für Inkompatibilitäten ist die Schreibweise für Datumskonstanten.<br />

Mit Escape-Klausel kann folgende Schreibweise für den 6.1.2003 benutzt werden: {d<br />

´2003-01-6´}<br />

Ergebnisgröße und Laufzeiten von Anfragen<br />

� Mit der Methode setMaxRows kann die maximal erwünschte Anzahl von Ergebnissen<br />

spezifiziert werden und mit setQueryTimeout die maximal akzeptierte Ausführungszeit.<br />

Seite 255


ResultSet<br />

getXXX<br />

Datentypen<br />

Wichtige Klassen bei JDBC<br />

executeQuery<br />

getResults<br />

executeQuery<br />

setXXX<br />

getXXX<br />

Statement<br />

IS-A<br />

PreparedStatement<br />

IS-A<br />

CallableStatement<br />

createStatement<br />

prepareStatement<br />

prepareCall<br />

Anwendungsprogrammierung<br />

Connection<br />

DriverManager<br />

getConnection<br />

� Die Namen in den Rechtecken entsprechen den Namen der verfügbaren Schnittstellen<br />

� Die gerichteten durchgezogenen Kanten zeigen, wie man ein Objekt einer Klasse (auf die eine<br />

Kante gerichtet ist) mit Hilfe der anderen Klasse erzeugt.<br />

Seite 256


PreparedStatement<br />

Anwendungsprogrammierung<br />

� Ein PreparedStatement ist eine Spezialisierung eines Statements, wobei die SQL-Anweisung<br />

beim Erzeugen des Statements (bis auf Parameter) vorliegen muß.<br />

– Dieses Statement wird bereits bei der Erzeugung übersetzt und kann ohne<br />

Neuübersetzung beliebig <strong>of</strong>t ausgeführt werden.<br />

– Eingabeparameter sind erlaubt, die erst bei Ausführung mit Werten belegt werden.<br />

� Bei der Definition eines PrepapredStatement werden die Eingabeparameter jeweils durch ein<br />

Fragezeichen markiert.<br />

– PreparedStatement stmt = con.prepareStatement(“select x, y from Points where x < ? and<br />

x > ?”);<br />

� Vor der Ausführung einer Anweisung müssen die Parameter durch set-Methoden gesetzt<br />

werden. Für jeden Typ gibt es eine spezielle Methode.<br />

– stmt.setInt(1, 20); stmt.setInt(2, 10);<br />

// Erste Parameter der set-Methoden ist die Stelle des Parameters in der<br />

// Anweisung.<br />

� Zur Übergabe von NULL-Werten und großen Objekten gibt es spezielle Methoden:<br />

– void setNull(int stelle, int jdbcType);<br />

// Der zweite Parameter identifiziert ein Typ, siehe java.sql.Types<br />

– void setAsciiStream(int stelle, java.io.InputStream s, int len);<br />

Seite 257


Ergebnisse von Anfragen<br />

Anwendungsprogrammierung<br />

� Anfragen mit Select-Klausel liefern als Ergebnis ein Objekt der Klasse ResultSet.<br />

– Repräsentation einer Menge von Tupeln mittels eines Cursors.<br />

� Methode next() liefert beim erfolgreichen Weitersetzen des Cursors true, wobei zu Beginn der<br />

Cursor vor dem ersten Tupel steht (Ein Aufruf von next ist deshalb vor dem ersten Zugriff<br />

zwingend erforderlich).<br />

� Zugriff auf die Spalten erfolgt über get-Methoden, wobei es für jeden Typ int, double, …<br />

jeweils eine solche Methode gibt.<br />

– Parameter der get-Methode ist die Position der Spalte in der Relation.<br />

– Eine Methode findColumn(String str) liefert zu einem Attributnamen die Position.<br />

– Eine weitere Besonderheit von JDBC ist die Methode getObject, die zu dem SQL-Typ<br />

einen passenden Java-Objekttyp generiert.<br />

� Null-Werte erfordern wiederum eine Sonderbehandlung.<br />

– boolean wasNull()<br />

überprüft, ob das zuletzt abgefragte Attribut tatsächlich ein Nullwert war.<br />

– Dieser Methodenaufruf ist nur in folgenden Fällen sinnvoll:<br />

a) Wenn die get-Methode den Wert null liefert.<br />

b) Wenn getBoolean den Wert false liefert.<br />

c) Wenn getInt und getDouble den Wert 0 liefert.<br />

Seite 258


7.1.4 Metadaten<br />

Anwendungsprogrammierung<br />

� Durch Ausnutzung der Metadaten der zugrunde liegenden Datenbank können Anwendungen<br />

erheblich flexibler gestaltet werden.<br />

� JDBC bietet folgende Schnittstellen für Metadaten an<br />

– ResultSetMetaData zur Beschreibung der Relation, die das Objekt der Klasse ResultSet<br />

verwendet.<br />

– <strong>Database</strong>MetaData zur Beschreibung der eigentlichen Datenbank<br />

ResultSetMetaData<br />

� ist insbesondere dann von Vorteil, wenn der Benutzer nicht genau weiß, welche der get-<br />

Methoden bei einem Objekt rs der Klasse ResultSet tatsächlich angewendet werden sollen.<br />

� Abhilfe schafft dann der Aufruf rs.getMetaData(), der zu rs die Metadaten liefert.<br />

� Damit kann z. B. die Anzahl der Spalten, der Typ und Name einer Spalte abgefragt werden.<br />

� Beispiel:<br />

ResultSet rs = stmt.executeQuery(“SELECT * FROM Personal”);<br />

ResultSetMetaData rsm = rs.getMetaData();<br />

Seite 259


for (int i = 1; i


7.1.5 Ausnahmebehandlung<br />

Anwendungsprogrammierung<br />

� Wie üblich in Java werden ungewöhnliche Situationen durch Verwendung des Exception-<br />

Konzepts behandelt. Hierfür gibt es eine eigene Klasse SQLException, auf die wir hier nur<br />

verweisen wollen.<br />

� Zusätzlich können “unkritische” Fehler auch als Warnungen nach außen gegeben werden.<br />

– Warnungen sind Objekte von der Klasse SQLWarning bzw. von SQLWarning<br />

abgeleiteten Klassen.<br />

– Beispiel: Klasse DataTruncation<br />

Eine solche Warnung wird beim Lesen von Daten gegeben, wenn diese nicht vollständig<br />

eingelesen werden konnten.<br />

Seite 261


Anwendungsprogrammierung<br />

7.1.6 Abbildung von SQL-Typen in Java<br />

� Da das Typsystem der verschiedenen DBMS recht unterschiedlich ist, bietet JDBC zur<br />

Überwindung der Inkompatibilitäten in der Klasse java.sql.Types einige generische<br />

Typbezeichner an.<br />

– z. B. VARCHAR, LONGVARBINARY, INTEGER, DOUBLE, DATE, TIME<br />

� Diese Typen (repräsentiert als ganzzahlige Konstanten) sind dann dort einzusetzen, wo SQL-<br />

Typen anzugeben sind. Die Umsetzung in die spezifischen Typen des zugrunde liegenden<br />

DBMS erfolgt automatisch über den Treiber.<br />

� Ähnliche Vorgehensweise steckt hinter den Aufrufen der getXXX- und setXXX-Methoden.<br />

– Es erfolgt hierbei eine Konvertierung von einem Java-Typ in einen JDBC-Typ und<br />

implizit durch den Treiber in einen Typ des zugrunde liegenden DBMS.<br />

� Darüber hinaus ist zu beachten, dass die Datums- und Zeittypen von Java aus dem Package<br />

java.sql stammen.<br />

– Diese sind im Wesentlichen Wrapper-Klassen für die aus dem Package java.util.<br />

Seite 262


Anwendungsprogrammierung<br />

7.1.7 Erweiterungen: JDBC 2 und JDBC 3+4<br />

Entwicklung von JDBC<br />

� Die bisherige Beschreibung entspricht im Wesentlichen dem ursprünglichen JDBC-Standard,<br />

der aber bereits 1998 wesentlich erweitert wurde (JDBC 2).<br />

� In Java 6 wird inzwischen JDBC 4 unterstützt.<br />

� JDB4-kompatible Treiber werden ebenfalls angeboten.<br />

Überblick der Erweiterungen<br />

� Scrollen auf Objekten der Klasse ResultSet, Unterstützung von Änderungsoperationen<br />

� Unterstützung von Typen aus SQL99 (JDBC3) und SQL 2003 (JDBC4)<br />

� Batch-Updates<br />

� Sicherungspunkte<br />

� Weitere optionale Änderungen im Package javax.sql<br />

Seite 263


Erweiterungen von ResultSet<br />

Anwendungsprogrammierung<br />

� Flexible Positionierung in einem ResultSet<br />

– vorwärts<br />

– rückwärts<br />

– direkt<br />

� Dies hört sich zunächst relativ unspektakulär an, hat aber erhebliche Auswirkungen. Es werden<br />

jetzt mehrere Typen von ResultSet angeboten<br />

– forward-only<br />

Das entspricht der zuvor beschriebenen Funktionalität von ResultSet.<br />

– scroll-insensitiv<br />

Dieser Typ unterstützt das Durchlaufen in beliebigen Richtungen, wobei sich Änderungen<br />

auf den Datenbestand nicht auswirken.<br />

– scroll-sensitiv<br />

Dieser Typ unterstützt ebenfalls beliebiges Navigieren, aber Änderungen von anderen<br />

Transaktionen werden dabei sichtbar.<br />

� Darüber hinaus wird noch unterschieden zwischen<br />

– read-only: keine Änderungen auf den Daten zulässig.<br />

– updatable: Änderungen, Löschen und Einfügen werden unterstützt.<br />

Seite 264


Anwendungsprogrammierung<br />

� Erzeugen von scrollbaren Objekten der Klasse ResultSet erfolgt über eine neue Methode, die<br />

zusätzlich zwei Parameter umfasst:<br />

– resultSetType (vom Typ int) spezifiziert den jeweiligen Typ<br />

– resultSetConcurrency (vom Typ int) gibt an, ob das Objekt nur lesbar oder auch<br />

änderbar ist.<br />

Beispiel:<br />

Statement stmt = con.createStatement( ResultSet.TYPE_SCROLL_INSENSITIVE,<br />

ResultSet.CONCUR_READ_ONLY);<br />

ResultSet srs = stmt.executeQuery("SELECT Name FROM Personal");<br />

� Dabei ist zu beachten, dass einige Treiber nicht die komplette Funktionalität unterstützen. Um<br />

sicher zu gehen, muss man auf die Methode<br />

boolean supportsResultSetType(int resultSetType)<br />

aus der Klasse java.sql.<strong>Database</strong>MetaData zurückgreifen.<br />

Seite 265


Scrollen<br />

Anwendungsprogrammierung<br />

� Initiales Positionieren eines ResultSet<br />

– void beforeFirst() // Cursor ist vor dem ersten Element<br />

– void afterLast() // Cursor ist hinter dem letzten Element<br />

– boolean first() // Cursor ist auf dem ersten Element<br />

– boolean last() // Cursor ist auf dem letzten Element<br />

� Navigieren auf einem ResultSet<br />

– Neben der Methode boolean next() gibt es noch die Methode<br />

boolean previous() // Setzt den Cursor auf das Vorgängerelement.<br />

– Darüber hinaus besteht die Möglichkeit den Cursor direkt auf eine absolute Adresse<br />

boolean absolute(int row)<br />

und auf eine Adresse relativ zum aktuellen Tupel<br />

boolean relative(int row)<br />

zu setzen. Dabei ist zu beachten, dass das erste Element die Position 1 besitzt.<br />

� Abfragen von der Cursorposition<br />

– Hierzu kann man direkt int getRow() aufrufen.<br />

– Zusätzlich gibt es noch Methoden boolean isBeforeFirst(), boolean isAfterLast(),<br />

boolean isFirst(), boolean isLast().<br />

Seite 266


Änderungsoperationen<br />

Anwendungsprogrammierung<br />

� Bei Änderungsoperationen auf ResultSet-Objekten ergibt sich die gleiche Problematik wie bei<br />

Sichten (Views), dass diese nämlich nur sehr eingeschränkt möglich sind.<br />

– Die Anfrage beinhaltet nur eine Relation und keine Verbundoperation.<br />

– Der Primärschlüssel ist Bestandteil der Ergebnisrelation.<br />

– Alle Attribute, die nicht NULL-Werte zulassen und keine Defaultwerte besitzen, sind<br />

ebenfalls Bestandteil der Ergebnisrelation.<br />

� Änderungen (Update eines bestehenden Tupel)<br />

– Diese Operation bezieht sich stets auf das aktuelle Tupel des ResultSet.<br />

– Spaltenwerte können über die updateXXX-Methoden geändert werden.<br />

rs.updateDouble(“price”, 9.99);<br />

– Nach den Änderungen auf einem Tupel muss noch die Methode<br />

rs.updateRow();<br />

gerufen werden, um die Änderung tatsächlich in die Datenbank zu übertragen.<br />

� Einfügen eines neuen Tupel<br />

– Jedes ResultSet-Objekt verfügt über einen internen Datensatz zum Einfügen. Das<br />

Einfügen kann analog zum Update vorbereitet und danach mt dem Aufruf von insertRow<br />

abgeschlossen werden.<br />

Seite 267


Anwendungsprogrammierung<br />

– Zuerst muss man an die richtige Stelle positioniert werden<br />

rs.moveToInsertRow();<br />

– Danach können über die updateXXX-Methoden die Attributwerte des neuen Tupel<br />

eingegeben werden.<br />

– Schließlich muss noch durch den Aufruf<br />

rs.insertRow();<br />

das neue Tupel übertragen werden.<br />

– Ein Aufruf der Methode moveToCurrentRow sorgt dafür, dass der Cursor auf der<br />

vorherigen Position steht.<br />

� Löschen eines Tupel<br />

– Zunächst muss auf das zu löschende Tupel navigiert werden. Danach kann durch Aufruf<br />

der Methode<br />

rs.deleteRow()<br />

das Tupel gelöscht werden.<br />

Sichtbarkeit von Änderungen<br />

� Damit kann man steuern, ab welchem Zeitpunkt eine Änderung im AWP tatsächlich sichtbar<br />

wird.<br />

– s<strong>of</strong>ort nach der Änderung<br />

– am Ende der Transaktion<br />

Seite 268


Problem<br />

Techniken zur Leistungssteigerung<br />

Anwendungsprogrammierung<br />

� Tupelweiser Zugriff auf ResultSet erfordert bei jedem next-Aufruf Kommunikation mit dem<br />

DBMS-Server.<br />

� Änderungsoperationen können nur einzeln an das DBMS übergeben werden.<br />

Prefetching von Resultaten<br />

� Statt nur das nächste Tupel werden die nächsten k Tupel vom DBMS-Server angefordert.<br />

Durch Aufruf der Methode void setFetchSize(int rows) wird die Anzahl der Ergebnisse pro<br />

Anforderung spezifiziert.<br />

Seite 269


Batch-Updates<br />

Anwendungsprogrammierung<br />

� Bündelung von mehreren Änderungsoperationen, die gemeinsam an die zugrunde liegende<br />

Datenbank geschickt werden.<br />

� Hierzu gibt es folgende Methoden<br />

– void addBatch(String sql); // Fügt eine neue Änderungsoperationen zum Batch<br />

– int[] executeBatch(); // Führt einen Batch aus, wobei als Ergebnis die<br />

// Anzahl der betr<strong>of</strong>fenen Tupel geliefert wird.<br />

Beispiel ( mit Relation Emp(Name,Gehalt)):<br />

� Sourcecode<br />

con.setAutoCommit(false);<br />

Statement stmt = con.createStatement();<br />

stmt.addBatch("INSERT INTO Emp " + "VALUES('Müller', 3000)");<br />

stmt.addBatch("INSERT INTO Emp " + "VALUES('Schmidt', 4000)");<br />

stmt.addBatch("INSERT INTO Emp " + "VALUES('Becker', 3500)");<br />

stmt.addBatch("INSERT INTO Emp " + "VALUES('Bauer', 900)");<br />

int [] updateCounts = stmt.executeBatch();<br />

con.commit();<br />

con.setAutoCommit(true);<br />

Seite 270


Connection Pooling<br />

Anwendungsprogrammierung<br />

� Problem<br />

– Herstellung der physischen Verbindung zum Server ist eine teuere Operation.<br />

– In vielen Web-Anwendungen werden ständig Verbindungen auf- und abgebaut, viele<br />

Verbindungen werden nicht im vollen Umfang genutzt.<br />

� Lösungsidee<br />

– Bereitstellung von logischen Verbindungen, die auf wenige physische Verbindungen<br />

abgebildet werden.<br />

� Funktionalität unter JDBC<br />

– initialPoolSize initiale Anzahl der physischen Verbindungen<br />

– minPoolSize minimale Anzahl der physischen Verbindungen<br />

– maxPoolSize maximale Anzahl der physischen Verbindungen<br />

– maxIdleTime Zeitdauer (in Sekunden) die eine physische Verbindung ungenutzt im<br />

Pool bleiben soll.<br />

� Erweiterung für PreparedStatements<br />

– Pooling von Statements (nicht nur von Verbindungen)<br />

Seite 271


7.1.8 Zusammenfassung<br />

Anwendungsprogrammierung<br />

� JDBC hat sich als relativ leicht zu nutzende Call-Schnittstelle für die Erstellung von AWP<br />

erwiesen.<br />

– Anfragen werden in Objekte der Klasse Statement gepackt<br />

– Resultat einer Anfrage steht als Objekt der Klasse ResultSet zur Verfügung<br />

� Flexible Programmierung durch Unterstützung von Metadaten<br />

� JDBC wurde in den letzten Jahren um weitere Funktionalität erweitert.<br />

– Insbesondere zur flexibleren und effektiveren Nutzung von ResultSet.<br />

– Unterstützung des neuen SQL-Standards (bisher noch nicht behandelt)<br />

– Weitere Erweiterungen sind optional und sind in dem Package javax.sql zu finden.<br />

� Nachteile von JDBC<br />

– Abbildung der Typen zwischen Java und dem JDBC-Treiber (indirekt also dem DBMS)<br />

muss vom Benutzer vorgenommen werden.<br />

– Viele Fehler treten erst zur Laufzeit auf.<br />

– So genannte JDBC-konforme Treiber unterstützen nur einen relativ geringen<br />

Befehlsumfang. Damit sind <strong>of</strong>t Applikationen abhängig von dem jeweiligen Treiber<br />

(alternativ könnten auch die Eigenschaften eines Treibers erst erfragt werden, was aber<br />

die Programmierung erheblich erschwert).<br />

Seite 272


7.2 Embedded SQL (eSQL, SQLJ)<br />

� Grundlegendes Prinzip: Verwendung eines Vorübersetzers<br />

� Statische Festlegung der Datenbankoperationen zur Übersetzungszeit<br />

– Typenüberprüfung zwischen AWP und Datenbank durch den Vorübersetzer<br />

– einfache Übertragung von Daten aus der Datenbank ins AWP<br />

� Verwendung des Cursor-Prinzips zum Durchlaufen von Relationen<br />

Quelldateien<br />

Vor-Compiler<br />

Host-Compiler<br />

Host-Linker<br />

Zwischencode<br />

DBMS-Biblio<strong>the</strong>k<br />

AWP DBMS-Server<br />

Datenbank<br />

Anwendungsprogrammierung<br />

Seite 273


SQLJ<br />

Anwendungsprogrammierung<br />

� Embedded SQL wurde zunächst für die Programmiersprache C entwickelt.<br />

� Auf Grund der großen Akzeptanz von Java und JDBC bieten führende Datenbankhersteller<br />

(IBM, Oracle, Sybase) einen entsprechenden Ansatz für Java unter dem Namen SQLJ an.<br />

� SQLJ nutzt dabei typischerweise JDBC zur Codegenerierung.<br />

SQLJ-Quelle<br />

Zusatzinformationen<br />

über die SQL-<br />

Anweisungen<br />

SQLJ-Compiler<br />

Java-Compiler<br />

Java-Quelle<br />

Bytecode<br />

SQLJ-Laufzeit<br />

SQLJ-Pr<strong>of</strong>il<br />

JDBC<br />

JDBC-Biblio<strong>the</strong>k<br />

DBMS-Server<br />

Datenbank<br />

Seite 274


Anwendungsprogrammierung<br />

Syntaktische Kennung von Datenbankoperationen im SQLJ-AWP:<br />

� #sql {SQL-Befehl}<br />

� Ein SQL-Befehl bezieht sich auf die Objekte der Datenbank. Eine Ausnahme sind die<br />

sogenannten Hostvariablen, die zur Kommunikation zwischen der Datenbank und dem AWP<br />

genutzt werden.<br />

– Eine Hostvariable wird wie eine gewöhnliche Variable von Java deklariert und genutzt.<br />

– Eine Hostvariable kann auch in einem SQL-Kommando angesprochen werden, indem<br />

dem Variablennamen ein “:” vorgestellt wird.<br />

� Man kann auch Hostvariablen dazu nutzen, Ergebnisse einer Anfrage aufzunehmen, wobei<br />

dann nur ein Tupel als Ergebnis geliefert werden darf und nicht eine Menge.<br />

– select-Klausel wird um das Schlüsselwort into gefolgt von Hostvariablen ergänzt.<br />

Beispiele<br />

� #sql {select A, B from R where B > :x}<br />

Hier wird der Wert der Hostvariablen x in den SQL-Befehl eingesetzt.<br />

� #sql {select A, B into :a, :b from R where Id = 7}<br />

– Das Ergebnis wird nun in die Hostvariablen a und b übertragen (Ann.: Id ist<br />

Schlüsselkandidat).<br />

– Die Typen der Hostvariablen müssen zu den SQL-Typen kompatibel sein.<br />

Seite 275


Anwendungsprogrammierung<br />

Öffnen einer Datenbankverbindung<br />

� Ähnlich wie bei JDBC braucht man in SQLJ einen Bezug zu einer bestehenden Datenbank.<br />

Aus diesem Grund kann nun ein Kontext definiert werden:<br />

#sql context Verbinden<br />

Danach kann Verbinden wie eine Klasse benutzt werden, die insbesondere folgenden Konstruktor<br />

besitzt:<br />

Verbinden verbindungsObject = new Verbinden("jdbc:oracle:thin:@venus.ma<strong>the</strong>matik.unimarburg.de:1521:Init_DB",<br />

"scott", "tiger");<br />

Dieses Kontextobjekt kann nun bei einem sql-Befehl noch zusätzlich angegeben werden:<br />

#sql (verbindungsObject) {select A, B from R where B > :x}<br />

� Wird bei einem sql-Befehl kein Kontextobjekt angegeben, so wird ein Defaultkontextobjekt<br />

genutzt, das zuvor aber erzeugt werden muss:<br />

DefaultContext ctx = new DefaultContext(DriverManager.getConnection(…));<br />

Seite 276


Anwendungsprogrammierung<br />

Anfrageformulierung mit Iteratoren<br />

� Für SQL-Anweisungen, die mehr als eine Antwort liefern, können nun Iteratoren (Cursor)<br />

definiert werden. Es wird unterschieden zwischen positionsbezogenen und namenbezogenen<br />

Iteratoren.<br />

� Positionsbezogene Iteratoren (Beispiel):<br />

– Deklaration:<br />

#sql public iterator Pos (String, int);<br />

Damit wird ein Iteratortyp Pos mit zwei Komponenten definiert.<br />

– Danach kann man eine Variable des Typs deklarieren:<br />

Pos x;<br />

– Ein sql-Befehl kann an diese Variable gebunden werden:<br />

#sql x = {select A, B from R where B > 10};<br />

– Der Zugriff auf die Ergebnismenge erfolgt dann i. A. in einer Schleife:<br />

while (true) {<br />

#sql {fetch :x into :a, :b}; // impliziter Aufruf von next<br />

if (x.endFetch()) break;<br />

System.out.println(a + “ verdient “ + b + “ €”);<br />

}<br />

Seite 277


Anwendungsprogrammierung<br />

– Freigabe der Ressourcen:<br />

x.close();<br />

� Namensbezogene Iteratoren<br />

– Deklaration:<br />

#sql public iterator Name (String A, int B);<br />

– Deklaration einer Variablen<br />

Name y;<br />

– Anbinden an einen SQL-Befehl:<br />

#sql y = {select A, B from R where B > 10};<br />

Die Ergebnisrelation muss alle im Attribut deklarierten Attribute enthalten!<br />

– Zugriff auf die Ergebnismenge:<br />

while (y.next())<br />

System.out.println(y.A() + “ verdient “ + y.B() + “ €”);<br />

Man beachte hierbei, dass<br />

- der Zugriff auf die Werte über Methodenaufrufe erfolgt, wobei der Name der<br />

Methode dem des Attributs entspricht.<br />

- Mit der Methode next wird auf das nächste Tupel zugegriffen.<br />

Seite 278


Mengenwertige Änderungs- und Löschoperationen<br />

Anwendungsprogrammierung<br />

� Solche Operationen verwenden auch Iteratoren, wobei die zu ändernde (löschende)<br />

Datenmenge an den Iterator gebunden wird.<br />

� Danach können folgendermaßen die Änderungen vorgenommen werden.<br />

#sql public iterator Name implements sqlj.runtime.ForUpdate (String A, int B)<br />

// Hierbei muss der Iterator die oben genannte Schnittstelle implementieren.<br />

…<br />

Name y;<br />

…<br />

#sql y = {select A, B from R where B > 10};<br />

…<br />

while (y.next())<br />

#sql {update R set B = B + 10 where current <strong>of</strong> :y}<br />

Damit wird nun der derzeit angesprochene Datensatz der Menge geändert.<br />

� Zusätzliche Eigenschaften eines Iterators können bei der Deklaration durch eine with-Klausel<br />

gesetzt werden.<br />

– #sql public iterator Name implements sqlj.runtime.ForUpdate (String A, int B) with<br />

(sensitivity=SENSITIVE);<br />

Seite 279


Anwendungsprogrammierung<br />

7.3 Prozedurale Erweiterung von SQL<br />

� Neben der Einbindung der SQL-Funktionalität in einer imperativen Programmiersprache,<br />

besteht auch die Möglichkeit, SQL um prozedurale Konzepte zu erweitern.<br />

– Dies ist bereits als Anhang zum SQL92-Standard unter dem Namen SQL/PSM (Persistent<br />

Stored Modules) berücksichtigt.<br />

– Oracle hat unter den Namen PL/SQL eine solche Erweiterung bereits frühzeitig definiert,<br />

die im industriellen Umfeld zur Entwicklung von AWPs genutzt wird.<br />

– Oracle und andere Anbieter (IBM) bieten inzwischen an, in Java codierte Prozeduren im<br />

DBS ablaufen zu lassen.<br />

� Primäres Ziel der prozeduralen Erweiterung von SQL<br />

– Bündelung von mehreren SQL.Befehlen unter einer aufrufbaren Einheit, die in der<br />

Datenbank persistent abgespeichert und auf dem Server ausgeführt wird.<br />

� Vorteile zu bisherigen Ansätzen<br />

– Serverseitige Ausführung der Prozeduren ==> Unabhängigkit vom Client<br />

– Leistungsverbesserung, da die Kommunikation zwischen Client und Server erheblich<br />

reduziert werden kann.<br />

– Zentrale Verwaltung von gemeinsam genutzter Funktionalität<br />

Seite 280


Vorgehensweise<br />

Anwendungsprogrammierung<br />

� Implementierung einer Prozedur oder Funktion<br />

� Installation der Prozedur auf dem Server<br />

� Registrierung der Prozedur auf dem Server<br />

– Hierzu benutzt man die SQL-Operationen create procedure bzw. create function.<br />

� Aufruf der Prozedur vom Client<br />

– Dies geschieht indirekt über das DBMS.<br />

Seite 281


7.3.1 PL/SQL<br />

Anwendungsprogrammierung<br />

� PL/SQL ist eine von Oracle entwickelte Erweiterung von SQL, die primär zur Erstellung von<br />

gespeicherten Prozeduren entwickelt wurde.<br />

– Syntax orientiert sich an der Programmiersprache Ada<br />

� PL/SQL bietet insbesondere die Möglichkeit, Prozeduren zu deklarieren und diese in SQL<br />

aufzurufen.<br />

Vorteile gegenüber einer Hostsprache<br />

� homogene Anbindung der imperativen Konzepte an SQL<br />

� Typkonvertierungen entfallen<br />

� plattformunabhängige Ausführung<br />

Nachteil:<br />

� Imperative Konzepte sind für eine vollständige Entwicklung von AWP nicht ausreichend.<br />

Seite 282


PL/SQL Block<br />

Anwendungsprogrammierung<br />

� Ein PL/SQL-Block besteht aus drei Teilen:<br />

– einem optionalen Deklarationsteil zur Deklaration von Variablen und Objekten,<br />

– einem Rumpf, in dem der Zustand der Variablen manipuliert wird,<br />

– einem optionalen Ausnahmebehandlungsteil, in dem Ausnahmen und Fehler zur Laufzeit<br />

behandelt werden.<br />

� Definition eines Blocks:<br />

[ is]<br />

[declare ]<br />

begin<br />

<br />

[exception ]<br />

end<br />

Seite 283


Deklarationsteil<br />

Anwendungsprogrammierung<br />

� Typdeklarationen<br />

– Neben den SQL-Typen, können Variablen PL/SQL Typen wie boolean haben.<br />

– PL/SQL unterstützt insbesondere auch die Definition von Record-Typen:<br />

type PersonTyp is record (Name varchar(50), Salary int);<br />

– Weiterhin erlaubt PL/SQL auch indirekt über Relationen und Variablen erzeugte Typen.<br />

� Variablendeklarationen<br />

– Eine Variable wird ähnlich wie bei SQL durch Nachstellen des Typs deklariert:<br />

ang PersonTyp;<br />

– Eine Besonderheit ist, dass die Datentypen der Relationen bei der Variablendeklaration<br />

benutzt werden können:<br />

ang Personal%rowtype;<br />

– Entsprechend wird durch<br />

ang2 ang%type;<br />

eine Variable vom Typ der Variable ang deklariert.<br />

– Ähnlich wie in Pascal erstreckt sich der Gültigkeitsbereich einer Variablen auf den<br />

lokalen Block und alle Blöcke, die in diesem enthalten sind.<br />

– Die grundlegende Operation für Variablen ist die Zuweisung. Das Symbol ist ’:=’ !<br />

Seite 284


Cursor<br />

Anwendungsprogrammierung<br />

� Ein Cursor unterstützt die sequentielle Verarbeitung einer Datenmenge.<br />

� Cursordeklarationen<br />

– konstanter Cursor<br />

cursor AlleAng is<br />

select *<br />

from Personal;<br />

– parametrisierter Cursor<br />

cursor interessantePersonen(von int, bis int) is<br />

select *<br />

from Personal<br />

where Lohn > von and Lohn < bis;<br />

� Cursor und ihre Attribute<br />

Gewisse Eigenschaften von Cursorn können zur Laufzeit durch Anhängen eines Suffix<br />

abgefragt werden:<br />

– %found : Der letzte Fetch-Befehl auf dem Cursor war erfolgreich.<br />

– %isopen : Der Cursor ist geöffnet<br />

– %rowcount : Anzahl der Tupel des Cursors<br />

Seite 285


Imperative Ablaufsteuerung<br />

Kontrollstrukturen<br />

� bedingte Anweisung<br />

if <strong>the</strong>n end if;<br />

� for-Schleife<br />

for in <br />

loop<br />

<br />

end loop;<br />

Verarbeitung eines Cursors<br />

Anwendungsprogrammierung<br />

� Öffnen eines Cursors<br />

open AlleAng;<br />

open interessantePersonen(1000, 2000);<br />

� Spezielles Schleifenkonstrukt für einen Cursor zur Verarbeitung einer Antwortmenge<br />

for ang in AlleAng<br />

loop<br />

<br />

end loop;<br />

Seite 286


Prozeduren und Funktionen<br />

Anwendungsprogrammierung<br />

� Eine Prozedur ist ein Block, der mit einem Namen versehen ist und optional über eine<br />

Parameterleiste verfügt.<br />

� Eine Funktion liefert durch den Befehl return stets ein Ergebnis.<br />

function totalSalary(von int, bis int) return int is<br />

declare<br />

p Personal%rowtype;<br />

total int;<br />

begin<br />

open interessantePersonen(von, bis);<br />

…<br />

return total;<br />

end;<br />

� Die Parameter können mit drei verschiedenen Optionen versehen sein: in, out, in out<br />

procedure run (par1 in Typ1, par2 out Typ2, par3 in out Typ3, …) is<br />

<br />

Seite 287


Gespeicherte Prozeduren<br />

Anwendungsprogrammierung<br />

� Mittels des Befehls create procedure können Prozeduren im Datenbanksystem in übersetzter<br />

Form abgespeichert werden.<br />

– Dies hat insbesondere den Vorteil gegenüber dem bisherigen Ansatz von PL/SQL, dass<br />

die Anweisungen nicht mehr übersetzt werden müssen.<br />

� Die Deklaration einer Prozedur (Funktion) folgt dem bereites vorher erläuterten Muster<br />

Cursor-Variablen<br />

� Es ist <strong>of</strong>t günstig, die Ergebnisse einer gespeicherten Prozedur durch Cursor-Variablen an das<br />

aufrufende PL/SQL-Programm zu geben.<br />

� Eine Cursor-Variable ist eine Referenz auf eine Liste von Datensätzen. Es wird zwischen<br />

folgenden Typen von Cursor-Variablen unterschieden:<br />

– starker Typ:<br />

type personenCurTyp is ref cursor Personal%rowtype;<br />

– schwacher Typ:<br />

type allCurTyp is ref cursor;<br />

Die Variablendeklaration wird wie üblich vorgenommen.<br />

� Zum Zeitpunkt der Deklaration hat die Cursor-Variable noch keinen Bezug zu einer Anfrage.<br />

Seite 288


Anwendungsprogrammierung<br />

� Anbindung einer Cursor-Variable an eine Anfrage<br />

– erfolgt erst beim Öffnen eines Cursors:<br />

open personenCurTyp for<br />

select * from Personal where Lohn > 1000;<br />

� Typische Verwendung<br />

– Öffnen einer Cursor-Variablen in der gespeicherte Prozedur/Funktion<br />

– Übergeben des Cursors an das AWP, wo dann die Datensätze verarbeitet werden.<br />

Trotz der vielen Vorteile, die Cursor-Variablen bieten, gibt es derzeit bei der Nutzung in Oracle<br />

noch sehr viele Einschränkungen:<br />

– Eine Cursor-Variable darf nicht im Update-Modus geöffnet werden.<br />

– Den Typ ref cursor gibt es nur in PL/SQL, aber nicht in SQL.<br />

Seite 289


Beispiel 1<br />

Anwendungsprogrammierung<br />

� Erhöhe das Gehalt der Angestellten um 10%, die bisher unter dem Durchschnitt verdient<br />

haben. Gib das aktuelle Durchschnittsgehalt aus, falls dieses 50000 überschreitet.<br />

declare<br />

dGehalt number;<br />

begin<br />

select avg(Lohn) into dGehalt from Personal;<br />

update Personal set Lohn = Lohn*1.1 where Lohn < dGehalt;<br />

select avg(Lohn) into dGehalt from Personal;<br />

if dGehalt > 50000 <strong>the</strong>n<br />

dbms_output.put_line(“Durchschnitt: “ || dGehalt);<br />

end if;<br />

commit;<br />

exception<br />

when o<strong>the</strong>rs <strong>the</strong>n dbms_output_line(“Fehler beim Update”);<br />

rollback;<br />

end;<br />

Seite 290


Beispiel 2<br />

Anwendungsprogrammierung<br />

� Berechne die Gehaltserhöhung der Angestellten in Abhängigkeit ihres bisherigen Gehalts.<br />

declare<br />

begin<br />

cursor angCursor is select Lohn from Personal for update <strong>of</strong> Lohn;<br />

angNr integer;<br />

angGehalt Personal.Gehalt%type;<br />

open angCursor;<br />

fetch angCursor into angGehalt;<br />

while angCursor%found<br />

if angGehalt > 60000<br />

update Personal set Lohn = Lohn*1.1 where current <strong>of</strong> angCursor;<br />

elsif angGehalt > 50000<br />

update Personal set Lohn = Lohn*1.15 where current <strong>of</strong> angCursor;<br />

else<br />

update Personal set Lohn = Lohn*1.2 where current <strong>of</strong> angCursor;<br />

Seite 291


end;<br />

end if;<br />

fetch angCursor into angGehalt;<br />

end loop;<br />

Anwendungsprogrammierung<br />

Seite 292


Gespeicherte Prozeduren in JDBC<br />

Anwendungsprogrammierung<br />

� Gespeicherte Prozeduren lassen sich mittels JDBC aufrufen, indem ein Objekt der Schnittstelle<br />

CallableStatement erzeugt wird.<br />

� Der Aufruf einer gespeicherten Prozedur erfolgt über die Methode prepareCall, die als<br />

Parameter eine Zeichenkette in Escape-Schreibweise hat.<br />

CallableStatement cstmt = con.prepareCall(“{call TestProc(?,?)}”);<br />

Parameter werden dabei wie in JDBC üblich mit dem Symbol ? gekennzeichnet.<br />

� Danach müssen die Werte der Eingabeparameter mit setXXX-Methoden gesetzt werden.<br />

cstmt.setString(1,’Schneider’);<br />

cstmt.setDouble(2,42.0);<br />

� Für die Ausgabeparameter muss vor der Ausführung noch der JDBC-Typ festgelegt werden<br />

(Ann.: 1. Parameter ist IN und der 2. Parameter InOut):<br />

cstmt.registerOutParameter(2,java.sql.Types.FLOAT);<br />

� Die Prozedur kann dann mit einem Aufruf von execute aufgerufen werden.<br />

� Danach können die Ausgabeparameter mit getXXX-Methoden ausgelesen werden.<br />

double res = cstmt.getDouble(2);<br />

Seite 293


Gespeicherte Funktionen in SQL<br />

Anwendungsprogrammierung<br />

� Gespeicherte Funktionen können innerhalb von SQL deklariert und auch aufgerufen werden.<br />

Aber es gelten folgende Einschränkungen:<br />

– Die Funktion darf keine Gruppierungsoperationen enthalten.<br />

– Alle Datentypen der Eingabe und der Ausgabe müssen dem Datenbanksystem bekannt<br />

sein (also keine PL/SQL-Typen)<br />

� Beispiel einer gespeicherten Funktion:<br />

create function simple(x in int) return int as<br />

begin<br />

return x / 101;<br />

end simple;<br />

� Beispiel des Aufrufs einer Funktion in einer SQL-Anfrage:<br />

select Name, simple(Lohn) from Personal;<br />

Seite 294


Anwendungsprogrammierung<br />

7.3.2 Trigger: Ein Anwendungsfall für<br />

gespeicherte Prozeduren<br />

� Ein Trigger ist eine gespeicherte Prozedur, die bei Erfüllung gewisser Kriterien oder als<br />

Seiteneffekt einer Änderungsoperation in der Datenbank vom DBMS implizit ausgeführt wird.<br />

– Eine Ausführung erfolgt immer dann, wenn ein bestimmtes Ereignis eintritt.<br />

� Trigger werden insbesondere zur Wahrung der Datenkonsistenz (dynamische<br />

Integritätsbedingungen) genutzt. Trigger gehen deshalb über eine reine Überprüfung des<br />

Datenbankzustands hinaus.<br />

– Ein Trigger kann z. B. dafür sorgen, dass Statistiken aktualisiert werden oder abgeleitete<br />

Spalten berechnet werden.<br />

� Ein Trigger besteht aus<br />

– einem Kopf, in dem Vorbedingungen zur Ausführung formuliert sind,<br />

– und einem PL/SQL-Block.<br />

� Trigger sind nicht im SQL92 Standard, haben aber eine hohe praktische Relevanz.<br />

Seite 295


Einführendes Beispiel<br />

Anwendungsprogrammierung<br />

� Im Folgenden betrachten wir eine Relation Pr<strong>of</strong>essoren, die als Attribut den Rang des<br />

Pr<strong>of</strong>essors besitzt (siehe Kemper/Eickler). Durch den folgenden Trigger wird verhindert, dass<br />

der Rang von Pr<strong>of</strong>essoren durch einen Update niedriger wird.<br />

create trigger keineDegradierung<br />

before update on Pr<strong>of</strong>essoren<br />

for each row<br />

when (:old.Rang is not null)<br />

begin<br />

if :old.Rang = “C3” and :new.Rang = “C2” <strong>the</strong>n :new.Rang := “C3”; end if;<br />

if :old.Rang = “C4” <strong>the</strong>n :new.Rang := “C4”; end if;<br />

if :new.Rang is null <strong>the</strong>n :new.Rang := :old.Rang end if;<br />

end;<br />

Seite 296


Kopf eines Triggers<br />

Anwendungsprogrammierung<br />

� Anlegen bzw. Verändern eines neuen bzw. bestehenden Trigger erfolgt über<br />

– create trigger bzw. replace trigger <br />

� Trigger-Ereignis<br />

– Jedem Ereignis wird der Zeitpunkt vorangestellt, wann der Trigger ausgelöst werden soll.<br />

before | after<br />

– Beim Ereignis wird unterschieden zwischen Ändern, Einfügen und Löschen.<br />

update [<strong>of</strong> [] on <br />

insert on <br />

delete on <br />

Es können auch gleichzeitig mehrere Ereignisse spezifiziert werden. In diesem Fall kann<br />

im Rumpf des Trigger durch<br />

if updating [(’’)] <strong>the</strong>n<br />

if inserting <strong>the</strong>n<br />

if deleting <strong>the</strong>n<br />

zwischen den einzelnen Ereignissen unterschieden werden.<br />

� Trigger-Typ<br />

Es wird unterschieden zwischen einen befehlsorientierten Trigger, bei dem der Trigger genau<br />

einmal ausgeführt wird und einem zeilenorientierten Trigger. Letzteres erfordert zusätzlich<br />

folgende Zeile:<br />

Seite 297


Anwendungsprogrammierung<br />

for each row<br />

Bei einem zeilenorientierten Trigger wird der Trigger für jedes geänderte Tupel einmal<br />

aufgerufen. Im Rumpf hat man dann die Möglichkeit, das alte Tupel über die Variable :old und<br />

das neue Tupel über :new anzusprechen. Ein anderer Zugriff innerhalb des Rumpfs ist aber<br />

nicht mehr möglich.<br />

� Trigger-Restriktion<br />

when <br />

– Hier können Bedingungen formuliert werden, welche die Ausführung des Rumpfs<br />

auslösen.<br />

– Bei einem zeilenorientierten Trigger kann man sich über :new und :old auf die neuen bzw.<br />

alten Tupel der Relation beziehen.<br />

� Trigger-Rumpf<br />

– Besteht aus einem PL/SQL-Block mit den obengenannten Modifikationen<br />

Seite 298


Beispiele<br />

� Protokollierung der Änderungen am Attribut Lohn einer Relation Personal<br />

create trigger LogGehalt<br />

before update on Personal<br />

for each row<br />

when (:old > 1333)<br />

begin insert into LogRel values(:old.Lohn, :new.Lohn, sysdate) end;<br />

� Zurücksetzen einer Änderung<br />

create or replace trigger CheckGehalt<br />

before update on Personal<br />

for each row<br />

when (:new.Lohn > 1500)<br />

begin :new.Lohn := :old.Lohn end;<br />

Probleme bei Triggern<br />

Anwendungsprogrammierung<br />

� Gewährleistung der Widerspruchsfreiheit der Trigger durch Anwender<br />

– Vermeidung von Aufrufzyklen bei Triggern<br />

– Terminierung<br />

� Trigger sollten nur dann zur Formulierung von Integritätsbedingungen genutzt werden, wenn<br />

dies nicht mit anderen Mitteln möglich ist.<br />

Seite 299


Anwendungsprogrammierung<br />

7.3.3 Java und Gespeicherte Prozeduren<br />

� Im Zuge des Erfolges der Programmiersprache Java im Umfeld von DBMS bieten derzeit<br />

einige DBMS (DB2, Oracle) die Möglichkeit, gespeicherte Prozeduren in Java zu<br />

implementieren.<br />

� Die Vorgehensweise ist sehr ähnlich zu der von PL/SQL:<br />

– Erstellen einer Quelldatei<br />

public class Hello {<br />

public static String world() { return “Hello World”;}<br />

}<br />

– Übersetzen der Quelldatei auf dem Client<br />

javac Hello.java<br />

– Übergeben der class-Datei an das DBMS<br />

loadjava -user scott/tiger Hello.class<br />

– Erzeugen einer SQL-Schnittstelle für die Prozedur<br />

create function HelloWorld return varchar as<br />

language java name ’Hello.world() return java.lang.String’;<br />

– Ausführen der gespeicherten Prozedur<br />

variable myString varchar[20];<br />

call HELLOWORLD() into :myString;<br />

print myString;<br />

Seite 300


Fazit<br />

Anwendungsprogrammierung<br />

� PL/SQL ist eine interessante Erweiterung von SQL, die schon vor Java eine<br />

plattformunabhängige Programmierung angeboten hatte.<br />

� SQL wird insbesondere durch gespeicherte Funktionen mächtiger.<br />

� PL/SQL wurde in jüngster Zeit um so genannte Table Functions erweitert. Diese unterstützen<br />

Cursor, die wie eine Relation in der from-Klausel von SQL genutzt werden können.<br />

– Dabei wird sogar eine bedarfsgesteuerte Ausführung solcher Cursor unterstützt, d.h. die<br />

Tupel werden auf Anforderung nach und nach erzeugt.<br />

� Obwohl nahezu jedes relationale DBMS gespeicherte Prozeduren anbietet und es einen<br />

Standard SQL/PSM gibt, sind die Lösungen in DBMS derzeit noch recht unterschiedlich.<br />

Seite 301


Anwendungsprogrammierung<br />

7.4 Weitere Kopplungsmöglichkeiten<br />

PASCAL/R: eine Erweiterung von Pascal für relationale Datenbanken<br />

� Erweiterung des Typsystems von PASCAL:<br />

– Datentyp RELATION entspricht “SET OF TUPLE”<br />

– Operationen der relationalen Algebra<br />

– Iteratoren (wie Cursor) für die Verarbeitung von Relationen<br />

Skriptsprachen<br />

� populärer Ansatz für die Erstellung von AWPs (z. B. Visual Basic)<br />

� Nachteil<br />

– keine strenge Typisierung<br />

– keine Standards (schlechte Wartung der Applikationss<strong>of</strong>tware)<br />

– Durchmischung von verschiedenen Konzepten aus dem Bereich Datenbanken,<br />

imperativen Programmierung, Benutzerschnittstellen und Regeln<br />

� Vorteil:<br />

– schnelle Erstellung von AWP mit graphischen Benutzeroberflächen<br />

– komfortable Entwicklungsumgebung<br />

Seite 302


8. Physische Datenorganisation<br />

� Datenbanken<br />

– externe Ebene<br />

– konzeptionelle Ebene<br />

– physische Ebene<br />

� Leistungsfähigkeit eines DBMS<br />

– maßgeblich bestimmt durch die Datenstrukturen auf der physischen Ebene<br />

� Abbildung der konzeptionellen Ebene auf die physische Ebene<br />

Zugriffsstrukturen<br />

Pufferorganisation<br />

Externspeicherverwalt.<br />

ext. Speichermedium<br />

Datenobjekte:<br />

� Datensätze<br />

� Relationen<br />

Datenobjekte:<br />

� Seiten<br />

� Dateien<br />

Physische Datenorganisation<br />

Abbildung<br />

?<br />

Seite 302


AWP 1 AWP 2 • • • AWP n<br />

Anfragebearbeitung<br />

logische Seitenreferenzen<br />

Systempufferverwaltung<br />

physische Seitenreferenzen<br />

Externspeicherverwaltung<br />

Plattenzugriffe<br />

Architektur<br />

Algorithmen<br />

Physische Datenorganisation<br />

– Implementierung der<br />

Operatoren der<br />

relationalen Algebra<br />

Zugriffstrukturen<br />

– Hilfsdatenstrukturen für<br />

den schnellen Zugriff auf<br />

die relevanten<br />

Datensätze<br />

Speicherstrukturen<br />

– Physische<br />

Repräsentation der<br />

Relationen<br />

Seite 303


Physische Datenorganisation<br />

8.1 Aufbau eines Magnetplattenspeichers<br />

� Magnetplatten<br />

– seit über 40 Jahren die Technologie zur persistenten Datenspeicherung<br />

� Eigenschaften<br />

– günstig: 10GB für 1€<br />

– robust<br />

– große Speicherkapazität: bis 1 TB/Platte<br />

– langsam<br />

� Entwicklung der Plattenspeichertechnologie<br />

Plattenspeicher 1957 Plattenspeicher heute<br />

(2.5” Durchmesser)<br />

0,85 Zoll Durchmesser<br />

RAID-Plattensysteme<br />

Seite 304


Physische Datenorganisation<br />

Funktionsweise von Plattensystemen<br />

� Festplatte besteht aus einem Stapel übereinander liegender Magnetplatten.<br />

– Jede Oberfläche hat einen Lese/Schreibarm.<br />

– Lese/Schreibarme bewegen sich synchron, wobei nur einer davon<br />

aktiv ist.<br />

� Strukturierung:<br />

– Zylinder, Spur und Sektor (Seite)<br />

– Zugriff über einen Kamm mit Schreib-/Leseköpfen, der quer zur<br />

Rotation bewegt wird<br />

� Zugriff auf Seiten<br />

– Positionierung des Schreib-/Lesekopfes (Seek)<br />

� Zeit für die Armbewegung [5 ms]<br />

– Warten auf den Sektor / Seite (Rotationsverzögerung)<br />

��halbe Rotationszeit der Platte [3 - 4,3 ms]<br />

– Übertragung der Seite (Transferzeit)<br />

��Zeit für Schreiben bzw. Lesen einer 4 KByte Seite [0,05 ms]<br />

– Kontrolle der Übertragung: Zeit des Platten-Controllers [ < 1 ms]<br />

Zeit für Zugriff einer Seite >> Zeit für Hauptspeicherzugriff !<br />

Seite 305


Systempuffer-Verwaltung<br />

� Umsetzung der logischen in physische Seitenadressen<br />

Schnittstelle:<br />

Physische Datenorganisation<br />

� Bereitstellen einer DB-Seite im DB-Puffer (zur exklusiven oder gemeinsamen Benutzung).<br />

� Bereitstellen einer neuen Seite<br />

� Freigeben einer Seite<br />

intern verwendete Funktionen:<br />

� Effiziente Suche im Puffer<br />

– Hash-Tabelle<br />

� Suche nach freiem Platz im Puffer (Frames)<br />

� Bestimmen einer Seite (Opfer), die aus dem Puffer entfernt wird.<br />

– Least-Recently-Used: Verkettung der Seiten nach dem letzten Zeitpunkt der Nutzung<br />

� Schreiben modifizierter Seiten<br />

– Erfolgt in Absprache mit der Transaktionsverarbeitung<br />

Seite 306


8.2 Speicherstrukturen<br />

Physische Datenorganisation<br />

� Datenbanken werden typischerweise auf eine Datei bzw. eine Menge von Dateien abgebildet.<br />

� Beim Anlegen der Datenbank werden noch wichtige Parameter mitgegeben:<br />

– Initiale Dateigröße<br />

– Maximale Dateigröße<br />

– Inkrementelle Größe<br />

� Beim Anlegen einer Relation wird der Relation eine initiale Seite zugewiesen.<br />

– Alle weiteren Seiten werden dann miteinander verkettet.<br />

Tuple-Identifier (TID auch RowID und RID genannt)<br />

� TID ist eine eindeutige Kennung des Datensatzes innerhalb der Datenbank. Dieser setzt sich<br />

zusammen aus der Seitenadresse und einer relativen Adresse innerhalb der Seite.<br />

Seitenadresse: 42<br />

Der markierte Datensatz hat die TID (42,3)<br />

Seite 307


Physische Datenorganisation<br />

– TIDs sind invariant bzgl. Verschiebungen innerhalb einer Seite<br />

� Die TID ändert sich auch nicht, wenn ein Datensatz in eine andere Seite verschoben wird.<br />

– Anlegen eines Stellvertreters in der ursprünglichen Seite, der auf die neue Position<br />

verweist.<br />

j<br />

(4711,j)<br />

Seitenadresse: 42 Seitenadresse 4711<br />

� Vorteil des TID-Konzepts<br />

– TID sind stabil<br />

� Nachteil<br />

– hohe Zugriffskosten, wenn es viele Stellvertreter gibt.<br />

==> Reorganisation der Datenbank<br />

Seite 308


Recordmanager<br />

� Komponente zur Verwaltung der Datensätze in Seiten<br />

Zentrale Aufgabe des Recordmanager<br />

Physische Datenorganisation<br />

� Für einen neuen Datensatz soll eine Seite mit genügend freiem Speicherplatz gefunden werden.<br />

– Ggf. muss hierfür eine neue Seite angefordert werden.<br />

� Wünschenswert wäre auch eine Ballung (Clusterung) der Datensätze:<br />

– Datensätze, die <strong>of</strong>t gemeinsam zugegriffen werden, sollen auch gemeinsam in einer Seite<br />

liegen.<br />

Unterscheidung<br />

� Datensätze mit konstanter Länge<br />

– einfache Lösungen: z. B. Verkettung der Seiten, die noch Platz haben.<br />

� Datensätze mit variabler Länge<br />

– relativ kompliziert<br />

Seite 309


Zugriff auf die Basisrelationen<br />

Bei Datenbanken unterscheidet man zwischen zwei Zugriffsarten:<br />

Physische Datenorganisation<br />

� Relationen-Scan<br />

– Durchlaufen der zu der Relation gehörenden Seiten.<br />

� Index-Scan<br />

– Zugriff erfolgt indirekt über eine Hilfsstruktur, in der die Verweise (TID) auf die<br />

Datensätze (zusammen mit z. B. einem Attribut) der Relation hinterlegt sind<br />

(4711,j)<br />

Index auf dem<br />

Attribut Lohn<br />

der Relation Personal<br />

(1000, (42,3)) (2100, (42,1)) (3000,(4711,2)<br />

Seitenadresse: 42 Seitenadresse 4711<br />

j<br />

Seite 310


Ziel:<br />

8.3 Indexstrukturen<br />

Physische Datenorganisation<br />

� Effizienter Zugriff auf die Datensätze einer Relation, die ein bestimmtes Prädikat erfüllen.<br />

� Strukturen sollen keinen erheblichen Mehraufwand verursachen.<br />

– Änderungsoperationen<br />

– Speicherplatz<br />

Klassifizierung<br />

� Eindimensionale Prädikate (bzgl. einem Attribut)<br />

– Exakte Prädikate: Dyn. Hash-Verfahren<br />

– Bereichsprädikate und exakte Prädikate: B + - Bäume<br />

� Mehrdimensionale Prädikate<br />

– Bereichsprädikate<br />

� Metrische Prädikate<br />

– Nachbarprädikate<br />

� Mengenbasierte Prädikate<br />

Seite 311


Anforderungen<br />

Allgemeine Ziele beim Entwurf von Indexstrukturen<br />

� Hohe Speicherplatzausnutzung<br />

� Kurze Antwortzeiten für eine Operation<br />

– Benötigte Zeit entspricht dabei der Anzahl der Seitenzugriffe<br />

Operationen<br />

Physische Datenorganisation<br />

� Suchanfragen<br />

– Einlesen einer Teilmenge der Daten einer Relation<br />

– Exakte Suche: select * from R where R.A = c<br />

– Bereichssuche: select * from R where c1 � R.A and R.A � c2<br />

� Einfügen, Löschen und Ändern<br />

– Reorganisationen der Daten des Index erforderlich<br />

– Reorganisationen sollen nur lokal auf einem kleinen Teil der Daten einwirken<br />

(dynamische Indexstrukturen)<br />

Seite 312


8.3.1 Suchbäume<br />

Physische Datenorganisation<br />

� Wichtige Datenstruktur für Hauptspeicher und Hintergrundspeicher zur Unterstützung von<br />

Bereichsprädikaten (siehe Prakt. Info II)<br />

Definitionen (Baum)<br />

� Ein Baum ist eine endliche Menge T von Elementen, Knoten genannt, mit:<br />

(1) Es gibt einen ausgezeichneten Knoten w(T), die Wurzel von T<br />

(2) Die restlichen Knoten sind in m � 0 disjunkte Mengen T 1 , …, T m zerlegt, die<br />

ihrerseits Bäume sind. T 1 , …, T m heißen Teilbäume der Wurzel w(T).<br />

� Der Grad eines Knotens x, deg(x), ist gleich der Anzahl der Teilbäume von x. Gilt deg(x) = 0,<br />

so nennt man x ein Blatt.<br />

� Jeder Knoten x außer w(T) hat einen eindeutigen Vorgänger vm(x), auch als Vater/Mutter<br />

bezeichnet.<br />

� Ein Pfad in einem Baum ist eine Folge von Knoten x1 , …, xn mit: xi = vm(xi+1 ), i = 1, …, n-1.<br />

Die Länge des Pfades ist n.<br />

� Die Höhe eines Baums entspricht der Länge des längsten Pfads.<br />

Seite 313


Definition (Suchbaum)<br />

Physische Datenorganisation<br />

� Sei auf der Menge T eine Ordnungsrelation “


Die schlechte Nachricht!<br />

Physische Datenorganisation<br />

� Einfache Abbildung von binären Knoten auf Seiten führt zu schlechten Strukturen.<br />

– im schlechtesten Fall: ein Knotenzugriff = ein Plattenzugriff<br />

– exakte Suche ist dann sehr teuer<br />

z. B. für 107 Datensätze beträgt die Höhe bereits 23<br />

� Binäre Suchbäume sind also nicht für die Verwaltung auf dem Externspeicher geeignet.<br />

binärer Baum ideale Baumstruktur für den Externspeicher<br />

Zentrale Frage (bis Ende der 60er Jahre):<br />

� Gibt es eine effiziente Zugriffsstruktur für einen seitenorientierten Externspeicher?<br />

Seite 315


Prinzipien<br />

8.4 B + -Bäume<br />

� Im Gegensatz zu binären Bäumen enthält ein Knoten viele Einträge/Sätze<br />

– 1:1-Beziehung zwischen Knoten und Seiten!<br />

– Daten werden exklusiv in den Blättern verwaltet<br />

� Basieren auf dem Konzept von<br />

– ISAM (Index Sequential Access Method)<br />

statisch: globale Reorganisation periodisch erforderlich<br />

– B-Bäumen (Bayer & McCreight, 1972)<br />

Funktionsumfang und Leistung<br />

� Leistung des B+-Baums hängt von dem Verzweigungsgrad b eines Knotens ab.<br />

� Suchfunktionen:<br />

– Exaktes Prädikat<br />

– Bereichsprädikat<br />

� Effizienz (Speicherplatz u. Antwortzeiten) ist asymptotisch unabhängig von der<br />

Einfügereihenfolge.<br />

Physische Datenorganisation<br />

Seite 316


Definition (B+-Baum)<br />

Ein B + -Baum vom Typ (b, c) ist ein Baum mit folgenden Eigenschaften:<br />

1. Jeder Weg von der Wurzel zum Blatt hat die gleiche Länge.<br />

2. Die Wurzel ist ein Blatt oder hat mindestens 2 und höchstens 2b-1 Söhne.<br />

3. Jeder Zwischenknoten hat mindestens b und höchstens 2b-1 Söhne.<br />

4. Jedes Blatt hat mindestens c und höchstens 2c-1 Einträge.<br />

� Zwischenknoten:<br />

– p i = Zeiger Sohnseite, k i = Schlüssel<br />

– es gilt stets: k i < k i+1 für 0 < i < m.<br />

� Blattknoten:<br />

p 0 k 1 p 1 k 2 p 2 • • • k m p m frei<br />

V k 1 TID 1 k 2 • • • k m frei<br />

TID 2<br />

– TID i = Verweis auf den Satz mit Schlüssel k i<br />

– N = Zeiger auf den rechten Blattknoten<br />

– V = Zeiger auf den linken Blattknoten<br />

TID m<br />

N<br />

Physische Datenorganisation<br />

Seite 317


Eigenschaften des B + -Baums<br />

Physische Datenorganisation<br />

� lokale Ordnungserhaltung:<br />

Für jeden Zwischenknoten Z mit j Schlüsseln k1 ,…,kj und (j+1) Söhnen p0 ,…,pj gilt:<br />

Für jedes i, 1 � i � j, sind alle Schlüssel in dem zu p i-1 gehörenden Teilbaum nicht größer als k i<br />

und k i ist kleiner als alle Schlüssel, die im Teilbaum von p i liegen.<br />

… … …<br />

�k i<br />

k i<br />

B + -Baum<br />

�k i<br />

Datenraum<br />

k i<br />

�k i �k i<br />

Seite 318


Beispiel<br />

� b=2, c=2<br />

� Beachte: b und c sind nur aus Gründen der Übersicht so klein gewählt!<br />

4 6<br />

1 TID 3 TID 4 TID 5 TID 6 TID 7 TID 9 TID 10<br />

TID<br />

Physische Datenorganisation<br />

Seite 319


Physische Datenorganisation<br />

Wie hoch kann ein B + -Baum werden?<br />

� Welche Höhe besitzt ein B + -Baum zur Abspeicherung von N Datensätzen im schlechtesten<br />

Fall?<br />

Oder anders gefragt:<br />

� Wie viele Datensätze müssen mindestens (dürfen höchstens) in einem B + -Baum der Höhe h<br />

sein?<br />

� Vereinfachende Annahme: b = c<br />

Wurzel hat mindestens 2 Einträge<br />

Zwischenknoten in der Ebene 2 hat mindestens b Einträge<br />

Zwischenknoten in der Ebene 3 hat mindestens b Einträge<br />

… b Einträge<br />

Blattknoten in der Ebene h hat mindestens b Datensätze<br />

Daraus ergibt sich, dass in einem B + -Baum der Höhe h mindestens 2*bh-1 Datensätze liegen. Es<br />

gilt also N � 2*b h-1 und somit<br />

N<br />

h �<br />

1 + log �--- �<br />

b = O�log �2� bN� � Besonderheit der asymptotischen Analyse: b ist keine Konstante<br />

Seite 320


Speicherplatz für den B + -Baum<br />

� Speicherplatzausnutzung (SPAN):<br />

minimal<br />

--------------------------------------------------------------------------------------erforderlicher<br />

Speicherplatz<br />

tatsächlich reservierter Speicherplatz<br />

Physische Datenorganisation<br />

� Im schlimmsten Fall<br />

– Jeder Knoten (mit Ausnahme der Wurzel) ist mit mindestens der Hälfte der möglichen<br />

Schlüssel gefüllt.<br />

– Ein B + -Baum braucht (im schlechtesten Fall) doppelt soviel Speicher wie ein optimal<br />

gefüllter Baum. Damit ergibt sich eine Speicherplatzausnutzung von mindestens 50%.<br />

� Im Durchschnitt<br />

– ln 2 (etwa 69%)<br />

Wie viele Einträge passen in einen Zwischenknoten der Größe 4 KB?<br />

– pro Zeiger: 4 Byte<br />

– pro Schlüssel: 16 Byte<br />

Dies ergibt ca. 200 Einträge in einem Zwischenknoten.<br />

Seite 321


Problem:<br />

Exakte Suche im B+-Baum<br />

Physische Datenorganisation<br />

� Gegeben ein Schlüssel k. Liefere den TID des Datensatzes r mit r.key = k in dem B+-Baum mit<br />

Wurzel root: EMQ(root, k).<br />

Algorithmus EMQ(Knoten p akt , Key k)<br />

readPage(pakt );<br />

IF (pakt ist ein Zwischenknoten)<br />

index = m; // m ist die Anzahl der Schlüssel im Zwischenknoten<br />

Bestimme im Knoten pakt den kleinsten Schlüssel ki , so dass k � ki .<br />

IF (es gibt solch ein ki )<br />

index := i-1;<br />

RETURN EMQ(pindex , k); // rekursiver Aufruf<br />

ELSE<br />

Bestimme im Knoten pakt den Datensatz (ki ,TIDi ) mit k == ki .<br />

RETURN (es gibt solch einen Datensatz) ? TIDi : NULL;<br />

END EMQ;<br />

Seite 322


Vereinfachende Annahme<br />

Beispiel<br />

� Es wird nur als Ergebnis geliefert, ob der Datensatz im Baum ist.<br />

� Suche den Datensatz mit Schlüssel 42.<br />

� Suche den Datensatz mit Schlüssel 41.<br />

9 28<br />

41<br />

46 67<br />

1 5 9 15 19 28 33 37 41 45 46<br />

53 59 67 71 83 99<br />

Physische Datenorganisation<br />

Seite 323


Bereichsanfrage im B + -Baum<br />

Physische Datenorganisation<br />

� Gegeben ein Schlüsselpaar low und up, low � up. Finde alle TID der Datensätze r mit low � r.key<br />

� up im B + -Baum mit Wurzel root: RQ(root, low, up)<br />

Algorithmus RQ(Knoten p akt ; Key low, Key up)<br />

Bestimme analog zur exakten Suche das Blatt first, in dem ein Datensatz mit Schlüssel<br />

low liegen könnte;<br />

res = ���pakt = first;<br />

LOOP<br />

ReadPage(pakt );<br />

FOREACH (r mit r.key in [low,up] im Knoten pakt )<br />

res += {r.TID}<br />

IF ((es gibt ein Datensatz r in pakt mit r.key � up) OR<br />

(pakt ist das am weitesten rechts liegende Blatt im B+-Baum))<br />

RETURN res;<br />

pakt := pakt .N; // Gehe zum rechten Nachbarknoten<br />

END RQ;<br />

Seite 324


� Suche alle Datensätze im Bereich [40, 52].<br />

9 28<br />

Beispiel<br />

41<br />

46 67<br />

1 5 9 15 19 28 33 37 41 45 46<br />

53 59 67 71 83 99<br />

Physische Datenorganisation<br />

Seite 325


Physische Datenorganisation<br />

Einfügen und Löschen in B + -Bäumen<br />

Meistens ist das Einfügen und Löschen sehr einfach:<br />

� Entspricht fast immer einer exakten Suche, dem Einfügen des neuen Satzes und dem<br />

Zurückschreiben des modifizierten Blatts (Datenseite).<br />

Manchmal treten aber folgende Problemfälle auf:<br />

� Was passiert, wenn die Seite keinen Datensatz mehr aufnehmen kann?<br />

1. Lösung: Einführung von Überlaufseiten und verketten mit der Primärseite.<br />

– Nachteil: Kosten für Suche, Einfügen und Löschen erhöhen sich.<br />

2. Lösung: Reorganisation der Datenstruktur<br />

– S<strong>of</strong>ort: Überlaufseiten werden nicht zugelassen. Reorganisation des B + -<br />

Baums soll aber lokal begrenzt bleiben.<br />

– Verzögert: kurzzeitige Verwendung von Überlaufseiten und spätere globale<br />

Reorganisation des Datenbestands.<br />

� Was passiert, wenn es zu wenige Datensätze in der Seite gibt?<br />

Seite 326


Einfügen im B + -Baum<br />

Physische Datenorganisation<br />

� Gegeben einen Datensatz r = (key,TID) und die Wurzel root des B + -Baums. Füge den Datensatz<br />

in den B + -Baum ein: Insert(root, r).<br />

Algorithmus Insert(Knoten p akt ; Record r)<br />

Suche nach dem Datensatz mit Wert r.key; // siehe EMQ(pakt , r.key)<br />

IF (Datensatz wurde gefunden)<br />

RETURN; // ggf. melde dies als Fehler<br />

Setze pakt auf das zuletzt gelesene Blatt;<br />

Füge r in pakt ein;<br />

WHILE (pakt ist übergelaufen)<br />

Teile die Sätze/Verweise in pakt in zwei gleich große Gruppen L und R, so dass<br />

alle Sätze/Verweise in L kleiner sind als die Sätze/Verweise in R;<br />

Speichere die Sätze/Verweise in R in einem neuen Knoten pneu und die in L in pakt ;<br />

Sei kmax der größte Schlüssel in L;<br />

pakt = (vm(pakt ) != NULL) ? vm(pakt ) : newRoot(pakt ); // Gehe zum Vater<br />

Füge das Paar (kmax , pneu ) in den Vaterknoten ein;<br />

END Insert;<br />

Seite 327


Spezialfall: Überlauf der Wurzel<br />

� Schleife wird spätestens durch eine Überlaufbehandlung der Wurzel beendet.<br />

� Durch den Aufruf der Methode newRoot wird eine neue Wurzel bereitgestellt:<br />

p akt<br />

p akt<br />

neue<br />

Wurzel<br />

Physische Datenorganisation<br />

– Der neue Wurzelknoten verfügt zunächst über nur einen Eintrag. S<strong>of</strong>ort danach wird dann<br />

der zweite Eintrag eingefügt.<br />

Seite 328


� Einfügen von 40 in folgenden B+-Baum<br />

– Suche nach dem Blatt<br />

Beispiel<br />

9 28<br />

41 46<br />

1 5 9 15 19 28 33 37 41 45 46 53 59 67<br />

9 28<br />

41 46<br />

1 5 9 15 19 28<br />

40<br />

33 37 41 45 46 53 59 67<br />

– Einfügen in das Blatt, Spalten des Blatts und Einfügen in den Vater<br />

9 28<br />

41 46<br />

(37, )<br />

1 5 9 15 19 28 33 37 40 41 45 46 53 59 67<br />

Physische Datenorganisation<br />

Seite 329


– Einfügen in die Wurzel, Spalten der Wurzel und Erzeugen der neuen Wurzel<br />

9 28<br />

Wichtige Eigenschaften beim Einfügen:<br />

41 46<br />

1 5 9 15 19 28 33 37 40 41 45 46 53 59 67<br />

� Einfügeoperation bleibt auf einen Pfad des B + -Baums beschränkt.<br />

– Pro Ebene wird höchstens ein neuer Knoten hinzugefügt.<br />

– Der Aufwand für das Einfügen eines Datensatzes beträgt O(logb N)<br />

� Beim Einfügen bleiben alle Invarianten des B + -Baums erhalten.<br />

37<br />

Physische Datenorganisation<br />

Seite 330


Löschen im B + -Baum<br />

Physische Datenorganisation<br />

� Gegeben ein Schlüssel k und die Wurzel des B + -Baums. Finde den Datensatz mit Schlüssel k<br />

im B + -Baum und entferne diesen.<br />

Problemfälle:<br />

� Wie kann verhindert werden, dass ein Knoten zu wenig Datensätze enthält?<br />

– Ausgleich mit einem Geschwisterknoten<br />

– Ggf. muss der Knoten mit einem Geschwisterknoten verschmolzen werden.<br />

� Was passiert, wenn ein Datensatz gelöscht wird, dessen Schlüssel auch als Referenz in einem<br />

Elternknoten benutzt wird?<br />

– Das stellt kein Problem dar, weil die internen Schlüssel nur eine Wegweiserfunktion<br />

besitzen.<br />

Löschen von 28<br />

9 28<br />

37<br />

41 46<br />

1 5 9 15 19 28 33 37 40 41 45 46 53 59 67<br />

Seite 331


Physische Datenorganisation<br />

Kosten für Suchen, Einfügen und Löschen<br />

� Exakte Suche, Einfügen und Löschen sind auf einen Pfad beschränkt<br />

� Im schlechtesten Fall ergeben sich folgende Kosten für den B+-Baum:<br />

exakte Suche: O(logb N)<br />

Bereichanfrage: O(logb N + r/b)<br />

Einfügen: O(logb N)<br />

Löschen: O(logb N)<br />

Praktische Überlegungen<br />

� Wie viele Datensätze können in einem B + -Baum der Höhe 4 gespeichert werden?<br />

Beispiel (b = c = 200, 4 KB pro Seite);<br />

– Im schlechtesten Fall: 2*200*200*200 = 16*106 Datensätze, 8*10 4 Datenseiten = 320<br />

MB Speicherplatz für die Blattebene des B + -Baums.<br />

– Im Durchschnitt: Da Knoten zu etwa 2/3 im Durchschnitt gefüllt sind, können<br />

voraussichtlich 2*200*270*270 = 29*106 Datensätze verwaltet werden. Es wird nun 430<br />

MB an Speicherplatz für die Blattebene benötigt.<br />

� In vielen Anwendungen:<br />

Wurzel im Hauptspeicher ==> 3 Plattenzugriffe für exakte Suche<br />

Seite 332


Cluster-Index<br />

8.5 Indexe in Datenbanken<br />

Physische Datenorganisation<br />

� Höchstens ein Index pro Relation kann als Cluster-Index angelegt werden:<br />

create clustered index MeinIndex on …<br />

� Durch einen Cluster-Index wird das Speicherlayout der Datensätze der Relation bestimmt.<br />

– Beispiel: DB2 von IBM<br />

(a) Datensätze werden entsprechend der Ordnung im Index auf die Seiten abgebildet.<br />

(b) Häufiges Einfügen zerstört die Ordnung.<br />

(c) Reorganisation der Relation (TEUER) clustert die Datensätze wieder.<br />

– Beispiel: SQL Server<br />

Sicherstellung der Eindeutigkeit durch einen Index<br />

� Durch Anlegen eines Index kann sehr effizient überprüft werden, ob die Bedingung eines<br />

Schlüsselkandidats erfüllt ist.<br />

� Anlegen eines unique-Index:<br />

create unique index MeinIndex on …<br />

Seite 333


Überblick<br />

9. Anfrageverarbeitung<br />

Anfrageverarbeitung<br />

� Übersetzungsverfahren für SQL-Anfragen<br />

– Scannen und Parsen von Anfragen<br />

– Generierung eines Operatorbaums, der sich aus Operatoren der erweiterten relationalen<br />

Algebra zusammensetzt.<br />

� Anfrageoptimierung<br />

– algebraisch:<br />

Ausnutzung äquivalenter Repräsentationen von Anfragen in der relationalen Algebra<br />

– kostenbasiert:<br />

Ausnutzung spezieller Implementierungen von Operatoren der relationalen Algebra<br />

� Implementierung der Operatoren<br />

– ONC-Schnittstelle<br />

� Algorithmen für spezifische Operatoren<br />

Seite 334


Problem:<br />

Motivation und Problemstellung<br />

Anfrageverarbeitung<br />

� Gegeben eine SQL-Anfrage. Erzeuge aus der Anfrage einen schnell ausführbaren (ideal wäre<br />

einen optimalen) Code.<br />

Schwierigkeiten bei der Transformation<br />

� Eigenschaften von SQL<br />

– nicht-prozedurale (deskriptive) Anfragesprache<br />

– zugriffspfad-unabhängiges (relationales) Datenmodell<br />

– Fakten und Beziehungen werden durch Werte dargestellt<br />

– Zugriff auf Satzmengen<br />

� Code wird repräsentiert als physischer Operatorbaum<br />

– prozedurale Darstellung einer Anfrage<br />

– Ausnutzung von Indexstrukturen (und TIDs)<br />

– Zugriff auf einzelne Datensätze<br />

Seite 335


Vorgehensweise bei der Übersetzung<br />

1. Parsen der Anfrage (lexikalische und syntaktische Analyse)<br />

– Scannen des Eingabestroms<br />

– Überführen der Anfrage in eine Interndarstellung<br />

2. Semantische Analyse<br />

– Ersetzen der Sichten durch ihre relationalen Ausdrücke.<br />

– Gibt es die in der Anfrage angesprochenen Relationen und Attribute<br />

tatsächlich in der Datenbank?<br />

– Zugriffskontrolle<br />

3. Normalisierung der Anfrage<br />

– Überführung in eine Normalform<br />

– Vereinfachung der Anfrage, d. h. Erkennen von Redundanzen und leeren<br />

Teilanfragen<br />

4. Erstellung von Ausführungsplänen und Auswahl des besten Ausführungsplans<br />

Anfrageverarbeitung<br />

Seite 336


9.1 Anfrage als Operatorbaum<br />

� Die übliche interne Darstellung einer Anfrage benutzt einen Operatorbaum:<br />

– Knoten stellen logische Operatoren der relationalen Algebra dar.<br />

– Kanten beschreiben den operator-kontrollierten Datenfluss.<br />

Anfrageverarbeitung<br />

� Beispiel:<br />

select AName,Gehalt<br />

from Abteilung, Personal<br />

where Abteilung.Nr = Personal.AbtNr and Personal.Gehalt < 4000 and AName = ’Spielzeug’<br />

AName = ’Spielzeug’<br />

AName,Gehalt<br />

�<br />

Abteilung<br />

� Operatorgraphen benutzen Operatoren der erweiterten relationalen Algebra<br />

– Gruppierung, verallgemeinerte Projektion (Map), Aggregation, Duplikateliminierung<br />

�<br />

�<br />

�<br />

Personal<br />

AName,Gehalt<br />

Gehalt < 4000<br />

Seite 337


Äquivalente Operatorbäume<br />

Anfrageverarbeitung<br />

� Zwei Operatorbäume sind äquivalent, wenn ihre Ergebnisse für beliebige Instanzen der<br />

beteiligten Relationen gleich sind.<br />

� Eine SQL-Anfrage hat keine eindeutige Darstellung als Operatorbaum<br />

– Es gibt sogar unendlich viele Darstellungen!<br />

� Falls eine Anfrage eine einfache Select-From-Where-Anfrage ohne Unteranfrage ist, kann<br />

diese direkt in relationale Algebra umgesetzt werden:<br />

– Erzeuge das kartesische Produkt der Relationen in der from-Klausel<br />

– Schränke das Ergebnis auf die Tupel ein, welche die Bedingung der where-Klausel<br />

erfüllen.<br />

– Projektion auf die in der select-Klausel angegebenen Attribute<br />

� AName,Gehalt<br />

� AName = ’Spielzeug’ AND Lohn < 4000 AND Abteilung.Nr = Personal.AbtNr<br />

Abteilung<br />

Personal<br />

� Als problematisch erweisen sich dabei Unteranfragen (siehe weiterführende Vorlesungen)<br />

Seite 338


Algebraische Anfrageoptimierung<br />

Ziel bei der Anfrageübersetzung<br />

� frühzeitiges Erkennen leerer Anfragen und gemeinsamer Teilanfragen<br />

� Minimierung der Anzahl der Zwischenergebnisse im Operatorbaum<br />

Vorgehensweise<br />

� Normalisierung der Prädikate in der where-Klausel:<br />

Durch Anwendung der Kommutativ-, Assoziativ- und Distributivregeln sowie der De<br />

Morgan’schen Regeln lässt sich die where-Klausel in folgende Formen übertragen:<br />

– konjunktive Normalform<br />

(Pi1 OR Pi2 OR …Pin ) AND … AND (Pj1 OR Pj2 OR … Pjm )<br />

– disjunktive Normalform<br />

(P h1 AND P h2 AND …P hx ) OR … OR (P kl AND P k2 AND … P ky )<br />

Die Prädikate P i sind dabei atomar.<br />

� Anwendung von Regeln für die Operatoren der relationalen Algebra<br />

– Operatoren wie Selektion möglichst früh ausführen<br />

=> Reduktion der Zwischenergebnisse<br />

Anfrageverarbeitung<br />

Seite 339


Join-Reihenfolgen<br />

� Die Vereinigung, das kartesische Produkt und der natürliche Verbund sind<br />

– kommutativ (R |X| S = S |X| R) und<br />

– assoziativ ((R |X| S) |X| T= R |X| (S |X| T)).<br />

Aufgrund dieser Eigenschaften können sehr viele äquivalente Umformungen von<br />

Operatorbäumen berechnet werden.<br />

� Assoziativität gilt aber i. A. nicht für den Theta-Join.<br />

Seien R, S und T Relationen mit A,C � <strong>RS</strong>R , B � <strong>RS</strong>S und D � <strong>RS</strong>T . Dann ist:<br />

(R |X| A>B S) |X| C>D T definiert, aber R |X| A>B (S |X| C>D T) nicht.<br />

Anfrageverarbeitung<br />

– Das Attribut C besitzt keinen Bezug zur Relation S und T.<br />

� Der zentrale Baustein bei der Anfrageoptimierung ist verantwortlich für die Bestimmung einer<br />

Reihenfolge für die Abarbeitung von Joins.<br />

– i. A. Beschränkung auf links-tiefe Bäume<br />

– approximative Lösung durch dynamische Programmierung<br />

Seite 340


Ziel:<br />

Kostenbasierte Anfrageoptimierung<br />

� Transformation des zuvor hergeleiteten logischen Operatorbaums in einen physischen<br />

Operatorbaum auf Basis eines einfachen und effektiven Kostenmodells.<br />

Realisierung<br />

Anfrageverarbeitung<br />

� Auswahl einer effizienten Implementierung für die Operatoren<br />

� Zusammenfügen von aufeinander folgenden Operatoren zu neuen Operatoren.<br />

So ist es z. B. möglich, eine Selektion und eine Projektion (ohne Duplikateliminierung) in<br />

einem Operator durchzuführen.<br />

� Festlegung eines Kommunikationsprotokolls zwischen zwei aufeinander folgenden Knoten im<br />

Operatorbaum.<br />

– Alle Operatoren erfüllen die ONC-Schnittstelle.<br />

– Die Ergebnisse der Teilbäume werden bedarfsorientiert berechnet.<br />

Die Alternative dazu wäre alle Ergebnisse eines Teilbaums zu berechnen, diese alle auf<br />

Platte zu speichern. Danach könnte Vaterknoten die Daten wieder einlesen.<br />

Seite 341


9.2 ONC-Protokoll<br />

Anfrageverarbeitung<br />

� In diesem Abschnitt betrachten wir Operatoren und ihre Implementierungen, die auf einer<br />

Relation bzw. zwei Relationen arbeiten.<br />

� Alle Operatoren erfüllen die so genannte ONC-Schnittstelle eines Iterators:<br />

– Open: Öffnet den Iterator<br />

– Next: Gibt das nächste Element<br />

– Close: Schließt den Iterator<br />

Auf Basis dieser Schnittstelle können beliebige Operatoren der Algebra miteinander kombiniert<br />

werden.<br />

Ziel bei der Implementierung der Operatoren<br />

� Bedarfsgesteuerte Produktion der Ergebnisse<br />

– Immer dann, wenn auf einem Operator Next aufgerufen wird, wird erst das nächste<br />

Ergebnis berechnet!<br />

– Vermeidung von teuren Preprocessing-Schritten und Abspeicherung von Ergebnissen auf<br />

dem Externspeicher.<br />

Seite 342


Anforderung an ONC<br />

Anfrageverarbeitung<br />

� Damit eine möglichst effiziente Verarbeitung gewährleistet wird, sollten die physischen<br />

Operatoren nicht blockieren, sondern erste Ergebnisse bereits dann liefern, wenn die<br />

Eingabemenge(n) nicht vollständig vorliegen.<br />

– Erste Ergebnisse sollten schnell erzeugt werden (Optimierungsziel).<br />

– Die durchschnittliche Antwortzeit für einen Aufruf von Next sollte niedrig sein.<br />

� Beim Open eines Operators werden die erforderlichen Parameter der Operatoren gesetzt (wie<br />

z. B. der benötigte Hauptspeicher) und die Metadaten berechnet.<br />

– Open wird beginnend bei der Wurzel rekursiv für die Kinderknoten im Operatorbaum<br />

aufgerufen.<br />

– Das Open eines Operators ist erst dann abgeschlossen, wenn die darunter liegenden<br />

Operatoren vollständig geöffnet sind.<br />

– Teilweise können die Verfahren sich noch zur Laufzeit an den tatsächlich verfügbaren<br />

Speicher anpassen (speicheradaptive Verfahren)<br />

� Vorteile:<br />

– Einfacher Austausch von Implementierungen<br />

– Keine Zwischenspeicherung von Ergebnissen<br />

Seite 343


Einfache Beispiele für ONC<br />

Anfrageverarbeitung<br />

� Erste Implementierungen für Projektion und Selektion erfüllen in einfacher Weise die ONC<br />

Schnittstelle.<br />

� Projektion: �X (R)<br />

next() {<br />

rec = R.next();<br />

return new Record(rec, X);<br />

}<br />

Bei der verallgemeinerten Projektion wird im Wesentlichen noch eine Funktion auf die<br />

Datensätze angewendet.<br />

� Selektion: �F (R)<br />

next() {<br />

do<br />

rec = R.next();<br />

while (!F(rec));<br />

return rec;<br />

}<br />

Die Selektion kann insbesondere durch Indexstrukturen, wie z. B. B+-Bäume, effizient<br />

unterstützt werden.<br />

Seite 344


Anfrageverarbeitung<br />

Bei den anderen Operatoren ist ONC nicht so einfach zu implementieren.<br />

� Durchlaufen mehrerer Relationen (z. B. beim Join)<br />

� Mehrmaliges Durchlaufen einer Relation (z. B. beim Gruppieren)<br />

� Anlegen von zusätzlichen Datenstrukturen notwendig, die aufgrund ihrer Größe i. A. auf dem<br />

Plattenspeicher abgelegt werden müssen.<br />

�<br />

Die Kosten bei diesen Operationen sind damit im Wesentlichen durch die<br />

benötigten I/O Operationen bestimmt.<br />

Einfache Lösung: Nested-Loops-Technik<br />

� Basieren auf dem Durchlaufen der Relation(en), wobei ein möglichst großer Anteil im<br />

Hauptspeicher gehalten wird, um bei einem erneuten Durchlauf I/O Operationen einzusparen.<br />

Prinzipielle Techniken für Entwurf effizienterer Lösungen<br />

� Externes Sortieren<br />

� Divide-and-conquer (z. B. mit Hashing)<br />

Seite 345


9.3 Partitionierende Verfahren<br />

� Verwendung einer Partitionierungsfunktion f:<br />

– Abbildung der Datensätze auf {0,…, p-1}.<br />

Phase 1<br />

Wertebereich des<br />

Schlüssels<br />

f<br />

Anfrageverarbeitung<br />

� Für jede Partition wird eine Pufferseite im Hauptspeicher reserviert.<br />

� Datensätze werden gelesen und mittels der Funktion f einer Partition zugeordnet, d. h.<br />

Datensätze werden in die zugehörige Pufferseite im Hauptspeicher geschrieben.<br />

� Falls eine Pufferseite voll ist, wird deren Inhalt auf eine Seite im Externspeicher übertragen.<br />

0<br />

1<br />

p-2<br />

p-1<br />

Hauptspeicher<br />

p = #Partitionen<br />

0<br />

1<br />

p-2<br />

p-1<br />

Externspeicher<br />

Seite 346


Phase 2:<br />

� Nach der vollständigen Partitionierung der Daten wird iterativ für jede der Partitionen<br />

folgendermaßen vorgegangen:<br />

a) Alle Daten der Partition werden in den Hauptspeicher gelesen.<br />

b) Das entsprechende Problem (z. B. Duplikatbeseitigung) wird dafür gelöst.<br />

Phase 3 (optional)<br />

Anfrageverarbeitung<br />

� Sollte eine Partition immer noch nicht vollständig in den Hauptspeicher passen, wendet man<br />

obiges Prinzip rekursiv an oder verwendet ggf. Nested-Loops.<br />

Seite 347


Leistung des Verfahrens<br />

Anfrageverarbeitung<br />

� Annahmen<br />

– Gleichmäßige Verteilung der Daten über die Partitionen, d. h. jede Partition besitzt etwa<br />

N/p Datensätze.<br />

– Verfügbarer Hauptspeicher M und Seitengröße C<br />

� Für p Partitionen wird insgesamt p*C Hauptspeicher zum Schreiben benötigt. Dazu kommt<br />

eine Seite zum Lesen der Eingabe.<br />

– M � p*C + C<br />

� Um das Verfahren in zwei Phasen ablaufen zu lassen, muss zusätzlich folgende Bedingung<br />

erfüllt sein:<br />

– M � N/p<br />

p�N�C ist die optimale Wahl für p, d. h. es gilt M �<br />

CN.<br />

� Anzahl der I/O Operationen: 2*N/C<br />

Seite 348


Idee<br />

Hybrides Partitionieren<br />

� Möglichst viele Daten sollen im Hauptspeicher verarbeitet werden und nur wenige in<br />

Partitionen ausgelagert werden.<br />

– Partition 0 verbleibt im Hauptspeicher<br />

Anfrageverarbeitung<br />

– Partitionen 1,…,p werden bei Bedarf auf den Externspeicher ausgelagert.<br />

Partition 0<br />

0<br />

1<br />

h<br />

verbleibt im<br />

Hauptspeicher<br />

-1 ({0,…,s-1})<br />

s-1<br />

q-2<br />

q-1 Wertebereich des<br />

Schlüssels<br />

Wertebereich der<br />

Funktion h<br />

h<br />

h -1 ({s,…,q-1})<br />

f<br />

0<br />

1<br />

p-1<br />

p<br />

Externspeicher<br />

p + 1 = #Partitionen, p < q<br />

Seite 349


Parameter des Verfahrens<br />

� Größe der Partition 0<br />

– Durch Verkleinerung des Grenzwertes s ist eine dynamische Anpassung der<br />

Größe der Partition 0 möglich.<br />

� p = Anzahl der “externen” Partitionen<br />

� Datenstruktur der Partition 0<br />

– Falls die Partition 0 sehr groß ist, ist eine effiziente Datenstruktur zur<br />

Verwaltung der Datensätze vorteilhaft.<br />

– In der Literatur wird i. a. vorgeschlagen, die Partition 0 durch eine Hashtabelle<br />

zu verwalten.<br />

Bemerkung<br />

Anfrageverarbeitung<br />

� Hybrides Partitionieren lohnt, falls die Größe der Eingaberelation R zwischen M und M 2 / C<br />

Datensätze liegt, d. h. ein (ideales) Partitionierungsverfahren benötigt einen<br />

Partitionierungsschritt (bzw. zwei Phasen)<br />

Seite 350


Wie viele externe Partitionen werden benötigt?<br />

� Parameter<br />

– p Anzahl der externen Partitionen<br />

– m Anzahl der Seiten im Hauptspeicher (= M / C)<br />

– n Anzahl der Seiten der Relation (= N / C)<br />

Wir nehmen an, dass jede der Partitionen aus m Seiten besteht.<br />

� Jede der externen Partitionen benötigt einen Ausgabepuffer. Weiterhin wird noch ein<br />

Eingabepuffer benötigt. Somit verbleiben<br />

m – �p + 1�<br />

Seiten für die Partition 0 im Hauptspeicher.<br />

� Berechne nun p so, dass p dem kleinsten Wert entspricht, für den gilt:<br />

� Nach Auflösung nach p ergibt sich dann<br />

m– �p+ 1�+<br />

mp � n<br />

p =<br />

�n – m + 1���m–<br />

1�<br />

Anfrageverarbeitung<br />

Aus dieser Gleichung lassen sich dann auch s<strong>of</strong>ort die Kosten für das hybride Hashverfahren<br />

abschätzen.<br />

Seite 351


Anfrageverarbeitung<br />

9.4 Aggregate und Duplikatbeseitigung<br />

� Implementierung von Aggregation und Duplikatbeseitigung durch einen Operator<br />

� Aggregatberechnung<br />

– Berechnung eines einzigen Werts für die gesamte Relation (Skalares Aggregat)<br />

select count(*)<br />

fromAngestellte<br />

where Gehalt > 20000<br />

– Berechnung eines Werts für jede Klasse einer Relation (Aggregatfunktionen)<br />

select AbtNr, count(*)<br />

from Angestellte<br />

where Gehalt > 20000<br />

group by AbtNr<br />

� Duplikateliminierung<br />

– ist beispielsweise nach einer Projektion mit distinct erforderlich<br />

select distinct Abteilung<br />

from Angestellte<br />

where Gehalt > 20000<br />

� Unterschied zwischen Duplikateliminierung und Aggregatfunktionen?<br />

Seite 352


Anfrageverarbeitung<br />

Duplikatbeseitigung durch Nested-Loops<br />

� Algorithmus DupElim(Eingabe Relation R, Ausgabe Relation S)<br />

S.insert(R[0])<br />

out: for (int i = 1; i < R.length(); i++) {<br />

for (int j = 0; j < S.length(); j++)<br />

if (R[i] == S[j])<br />

continue out;<br />

S.insert(R[i]);<br />

}<br />

� Algorithmus hat im schlimmsten Fall quadratische Laufzeit.<br />

Was tun, wenn R und S nicht in den Hauptspeicher passen?<br />

� Für jedes Tupel der Relation R teste, ob das Tupel bereits im Hauptspeicherteil von S liegt.<br />

– Wenn ja, wird dieses Tupel verworfen.<br />

Andernfalls wird überprüft, ob das Tupel noch in den Hauptspeicher passt.<br />

– Wenn ja, fügen wir das Tupel in den Hauptspeicherteil von S ein.<br />

Andernfalls, speichern wir es auf dem Externspeicher in einer Datei R’ ab.<br />

� Danach wird der Hauptspeicher geleert und der Algorithmus wird rekursiv für R’ aufgerufen.<br />

Seite 353


Wie kann ONC implementiert werden?<br />

Anfrageverarbeitung<br />

� In der open-Phase wird im Wesentlichen der Hauptspeicher reserviert und das erste Tupel<br />

eingefügt (und als aktuelles Tupel markiert).<br />

� In der next-Phase wird<br />

– das aktuelle Tupel ausgegeben,<br />

– und ein neues Tupel in den Hauptspeicher geholt (dies kann insbesondere dazu führen,<br />

dass die Relation R’ erzeugt werden muss).<br />

Vorschläge zur Leistungsverbesserung<br />

� Die im Hauptspeicher liegenden Daten von S können durch einen Index organisiert werden,<br />

der Suchen und Einfügen effizient unterstützt.<br />

� Verwendung eines Bitfilters<br />

Seite 354


Sortieren<br />

Duplikatbeseitigung<br />

durch Sortieren und Hashing<br />

Anfrageverarbeitung<br />

� direkte Anwendung externer Sortierverfahren<br />

� Vorschlag zur Leistungsverbesserung<br />

– Duplikatbeseitigung sollte so früh wie möglich durchgeführt werden, d. h. in den frühen<br />

Phasen des Verschmelzens sollten bereits Duplikate beseitigt werden.<br />

– Beobachtung von Bitton & DeWitt:<br />

Durch eine frühe Duplikatbeseitigung werden die sortierten Teilfolgen nicht wesentlich<br />

verkürzt. Erst beim letzten Verschmelzen werden viele Duplikate beseitigt.<br />

Hashing<br />

� Aufteilen der Daten in Partitionen, die komplett in den Hauptspeicher passen.<br />

� Eliminierung von Duplikaten aus den einzelnen Partitionen<br />

� Wenn möglich hybrid: frühe Produktion von Ergebnissen möglich.<br />

Seite 355


Zusammenfassung<br />

� Implementierung von SQL-Übersetzern<br />

� Anfrageoptimierer ist die zentrale Komponente<br />

– algebraisch<br />

– kosten-basiert<br />

� Bedarfsgesteuerte Implementierung der Operatoren<br />

– ohne Speicherung großer Zwischenergebnisse<br />

� Implementierungstechniken<br />

– nested-loops<br />

– sortierbasiert<br />

– hash-basiert<br />

� Beispiel für Duplikateliminierung<br />

Anfrageverarbeitung<br />

Seite 356


Übersicht<br />

10. Data-Warehouse<br />

� Klärung wichtiger Begriffe<br />

� Architektur eines Data-Warehouse<br />

� Back-End Komponenten<br />

� Front-End Komponenten<br />

� Implementierung eines Data-Warehouse durch relationale Datenbanksysteme<br />

Data-Warehouse<br />

Seite 357


Data-Warehouse<br />

Online-Transaction Processing (OLTP)<br />

� OLTP bestimmte im Wesentlichen die Entwicklung bei der Datenbanktechnologie bis<br />

Mitte der 90er Jahre.<br />

� Charakterisierung von OLTP-Anwendungen<br />

– kurze Transaktionen<br />

– wenig Datenzugriffe pro Transaktion<br />

– viele Änderungen<br />

– keine historischen Daten, d. h. beim Ändern werden Daten überschrieben<br />

� Beispielsanwendungen<br />

– Buchungssysteme: Buchung eines Flugs<br />

– Bestellung von Waren<br />

– …<br />

� Optimierung dieser Datenbanken führte zu der Theorie der Normalformen.<br />

Normalisiertes Schema ist<br />

– gut für Datenbanken mit häufigen Änderungsoperationen.<br />

– schlecht bei anfrageintensiven Anwendungen.<br />

Seite 358


Online-Analytical Processing (OLAP)<br />

Data-Warehouse<br />

� Seit 10 Jahren stehen Anwendungen im Vordergrund, die sich mit der Analyse der Daten<br />

aus verschiedenen heterogenen Datenbanken beschäftigen.<br />

� Charakterisierung von OLAP-Anwendungen<br />

– lange Transaktionen<br />

– hohe Anzahl an Datenzugriffen pro Transaktion<br />

– lesender Zugriff auf Daten, “keine” Änderungen<br />

– Zugriff auf historische Daten<br />

� Beispiele<br />

– Auslastung der Atlantikflüge über den Zeitraum der letzten 2 Jahren<br />

– Verkaufszahlen in einem Gebiet in einer Produktgruppe in einem Zeitintervall:<br />

Wie viel Kaffee wurde in Marburg im letzten Jahr verkauft?<br />

� Optimierung solcher Datenbanken führt zu der Einführung von Redundanz, um (lesende)<br />

Anfragen effizient zu unterstützen.<br />

� Redundante Daten werden in einer separaten Datenbank, dem Data-Warehouse,<br />

gehalten.<br />

– Unabhängigkeit von den operativen Systemen<br />

Seite 359


10.1 Data-Warehouse - eine Definition<br />

Definition (Immon)<br />

Data-Warehouse<br />

� Ein Data-Warehouse ist eine <strong>the</strong>menorientierte, historische und autonome Datenbank<br />

eines Unternehmens, in der Daten aus verschiedenen unabhängigen heterogenen<br />

Quellsystemen integriert und verwaltet werden. Ziel ist, einem Unternehmen durch<br />

zeitbezogene Abfragen und Analysen entscheidungsunterstützende Ergebnisse zu liefern.<br />

Themenorientierung<br />

� Entscheidungsrelevante Sach<strong>the</strong>men eines Unternehmens stehen im Vordergrund<br />

– umsatzstärkste Kunden<br />

– kostenintensivste Produkte<br />

Man spricht dann auch von einer multidimensionalen Datenbank.<br />

Integration<br />

� Verknüpfung der Daten aus verschiedenen heterogenen Datenbanken<br />

� Passiver Ansatz (lazy, on demand)<br />

– Extraktion der Daten aus den Quellsystemen bei der Anfrageausführung<br />

Seite 360


� aktiver Ansatz (eager, in advance)<br />

– kein Zugriff auf Quellsysteme bei der Anfrageausführung<br />

– Extraktion im voraus<br />

� Gründe für den aktiven Ansatz im DW<br />

– Vermeiden der langsamen Zugriffe auf die Quellsysteme<br />

– Verfügbarkeit von Quellsystemen nicht erforderlich<br />

– Wenig Beeinträchtigung der Performance der Quellsysteme<br />

– Analysen und Anfragen erfordern i.A. nicht die neuesten Daten<br />

– Anreicherung der Daten bei der Extraktion<br />

– Historische Daten werden im DW aufbewahrt (kein Löschen der Daten)<br />

Zeitbezug<br />

� Daten liegen im DW in mehreren Versionen (bzgl. Zeit) vor.<br />

� Anfragen können sich nun auf einen Zeitpunkt bzw. Zeitraum beziehen.<br />

Autonomie<br />

� DW ist eine eigenständige und voll funktionsfähige Datenbank, die bezgl. der<br />

spezifischen Anforderungen optimiert ist.<br />

Data-Warehouse<br />

Seite 361


Data-Warehouse<br />

10.2 Das mehrdimensionale Datenmodell<br />

� Entscheidungsunterstützung basiert auf einem mehrdimensionalen Datenmodell<br />

(konzeptionelle Ebene)<br />

Bestandteile des Datenmodells<br />

� Messgrößen (Fakten)<br />

– numerische Wertebereiche<br />

– Beispiele: Umsatz, verkaufte Einheiten, Kosten, Deckungsbeitrag<br />

� Dimensionen<br />

– Messgrößen liegen in einem mehrdimensionalen Kontext<br />

– Beispiel: Umsatz hängt z. B. ab von den Dimensionen Produkt, Ort und Zeit. Diese<br />

Dimensionen bezeichnet man auch als die “natürlichen Parameter” von Umsatz.<br />

– Dimension setzt sich zusammen aus mehreren Attributen. Z. B.: Ort besitzt als<br />

Attribute Region, Land und Geschäft.<br />

– Ein Attribut einer Dimension ist eindeutig (innerhalb der Dimension).<br />

– Attribute einer Dimension sind <strong>of</strong>t hierarchisch strukturiert<br />

Tag, Monat, Jahr (d h. es bestehen FDs zwischen den Attributen)<br />

Seite 362


Land<br />

Region<br />

Geschäft<br />

Repräsentation als Datenwürfel<br />

Tag<br />

Monat<br />

Quartal<br />

Jahr<br />

Produkthauptgruppe<br />

Produktgruppe<br />

Produkt<br />

Data-Warehouse<br />

Produkt: Jacobs Krönung<br />

Geschäft: Tegut, Cappel<br />

Tag: 10.6.2009<br />

Umsatz: 47,11 Euro<br />

Seite 363


10.3 Architektur eines DW-<strong>Systems</strong><br />

Data<br />

Mart Data<br />

Mart Data<br />

Marts<br />

Extraktor<br />

Quelle<br />

OLAP Front-End-Tool, Data-Mining-Tool<br />

Data-Warehouse<br />

Integrator<br />

Extraktor<br />

Quelle<br />

Metadaten<br />

Extraktor<br />

Quelle<br />

Data-Warehouse<br />

Administrations- &<br />

Monitoring-Komponente<br />

Seite 364


10.3.1 Back-End Komponenten<br />

Voraussetzung für eine effektive Extraktion und Integration<br />

� Zustand der Quellsysteme<br />

� Konsistenz zwischen den Quellsystemen (wenn möglich)<br />

Integration<br />

1. Phase: Schrubben der Daten (data scrubbing)<br />

– Eliminierung von Duplikaten<br />

– Einfügen von Default-Werten<br />

– Korrektur von Fehlereingaben<br />

– Aufspüren von Integritätsverletzungen und “ungewöhnlichen” Daten<br />

2. Phase: Transformation<br />

– Vereinheitlichung von Maßeinheiten, Attributsnamen, Attributswerten<br />

– Ableitung von betriebswirtschaftlichen Kennzahlen<br />

Data-Warehouse<br />

Seite 365


Besonderheiten bei der Integration<br />

Data-Warehouse<br />

� Datenanreicherung bei der Integration<br />

– Zusammenführung von Daten aus verschiedenen Quellen<br />

(z. B. Kunde mit Bonitätspr<strong>of</strong>il)<br />

– Dies erfordert jedoch, dass die Daten über den gleichen Schlüssel verfügen.<br />

Ansonsten benötigt man Heuristiken, um Duplikate zu erkennen.<br />

� Berücksichtigung der Detailstufe (bei der Zeit)<br />

� Metadaten unterstützen den Abbildungsprozeß zwischen den Modellen der Quellsysteme<br />

und dem Modell des Data-Warehouse.<br />

Seite 366


Laden von Daten ins DW<br />

Data-Warehouse<br />

� Datenimport kann manuell, periodisch oder ereignisgesteuert ausgelöst werden.<br />

� Eine komplette Neuerzeugung des DW ist zu aufwendig<br />

– Stattdessen findet ein inkrementelles Laden der Daten ins Data-Warehouse statt.<br />

Problem:<br />

� Wie können Änderungen im Quellsystem erkannt werden?<br />

� Data Shipping<br />

Anlegen einer speziellen Log-Datei, in die Änderungen (mittels Trigger)<br />

hineingeschrieben werden.<br />

� Transaction Shipping<br />

Log-Datei des TA-Managers wird durchsucht.<br />

Aufbau und Erhaltung spezieller Datenstrukturen im DW<br />

� Anpassen von “materialisierten” Sichten<br />

� Einfügen der Daten in Indizes<br />

Seite 367


Administrative Metadaten<br />

Verwaltung der Metadaten<br />

� konzeptionelles (mehrdimensionales) Schema<br />

� logisches Implementierungsschema (z. B. im relationalen Modell)<br />

� vordefinierte Berichte<br />

� Beschreibung der Quellsysteme<br />

� Regeln zur Transformation und Archivierung<br />

Applikationsspezifische Metadaten<br />

� Verzeichnis über die Anwendungsterminologie. Man nennt dies auch Onthologie.<br />

Operationale Metadaten<br />

� Statistiken des laufenden Betriebs<br />

– Antwort- und Ladezeiten<br />

– Nutzung von Indizes und materialisierten Sichten<br />

Data-Warehouse<br />

Seite 368


Anforderung<br />

10.3.2 Front-End Komponenten<br />

Data-Warehouse<br />

� Anwender (z. B. Manager eines Unternehmens) soll selbständig und interaktiv das Data-<br />

Warehouse durchsuchen können.<br />

– Kennzahlenvergleich<br />

– Ursachenanalyse<br />

� Um diesen Anforderungen gerecht zu werden, stellt die OLAP-Engine einige<br />

Basisoperationen auf dem Hyperwürfel zur Verfügung<br />

� Präsentation der Ergebnisse einer Operation in Form von Pivottabellen (Kreuztabellen).<br />

Produkt Ort Zeit Umsatz<br />

Kaffee Cappel Januar 47,11<br />

Kaffee Wehrda Februar 333,33<br />

Kaffee Cappel Januar 99,01<br />

Obst … … …<br />

flache Tabelle<br />

Kaffee<br />

Ort<br />

Zeit<br />

Produkt<br />

Seite 369


Beispiel einer Pivottabelle:<br />

Data-Warehouse<br />

� Die Dimension Produkt wurde auf die Produktgruppe Kaffee “eingefroren”. Man spricht<br />

dann auch vom Ausblenden einer Dimension<br />

� Kaffeeumsatz wird jetzt in Abhängigkeit der angezeigten Dimension, Ort und Zeit<br />

veranschaulicht.<br />

Mehrdimensionale Pivottabellen<br />

Januar Februar März Summe<br />

Cappel 574,11 550,20 1200,30 2324,61<br />

Wehrda 808,80 770,77 500,34 2079,91<br />

Kernstadt 478,30 450,28 289,89 1217,47<br />

Summe 1861,21 1771,25 1990,53 5622,99<br />

� Durch Verschachtelung zweier Dimensionen können mehr als zwei Dimensionen in einer<br />

Pivottabelle veranschaulicht werden. Welche Spalten fehlen hier noch?<br />

Januar Februar März<br />

Obst Cappel 574,11 550,20 1200,30<br />

Wehrda 808,80 770,77 500,34<br />

Spielzeug Cappel 89,89 91,91 1000,01<br />

Wehrda 890,89 78,34 888,90<br />

Seite 370


Rotation<br />

Data-Warehouse<br />

� Vertauschen von angezeigten und ausgeblendeten Dimensionen.<br />

� Im Fall eines dreidimensionalen Würfels entspricht dies einer Rotation um 90 Grad<br />

Ort<br />

Zeit<br />

Produkt<br />

Januar<br />

angezeigte Dimensionen: Produkt, Ort<br />

ausgeblendete Dimension: Zeit<br />

eingefrorener Zeitpunkt: Januar<br />

Ort<br />

Produkt<br />

Zeit<br />

angezeigte Dimensionen: Zeit, Ort<br />

ausgeblendete Dimension: Produkt<br />

eingefrorenes Produkt: Kaffee<br />

Kaffee<br />

Seite 371


Roll-Up/Drill-Down<br />

Anfragemuster in SQL<br />

� Roll-Up<br />

– Erhöhung der Aggregationsstufe<br />

– Verdichtung der Messgrößen im Würfel<br />

� Drill-Down<br />

– inverse Operation zu Roll-Up<br />

– Reduzieren der Aggregationsstufe<br />

– Erhöhung des Detailgrads der Daten<br />

� Bei diesen Operationen werden sehr <strong>of</strong>t bereits die Attributshierarchien genutzt<br />

Weitere Operationen<br />

� Ranking<br />

– Was sind die zehn umsatzstärksten Kaffeemärkte?<br />

� Sortieren<br />

� Gruppieren / Aggregate<br />

� Ausnahmebehandlung<br />

Data-Warehouse<br />

Seite 372


Ziel<br />

Data Mining<br />

� Unterstützung der Ursachenanalyse<br />

� automatische bzw. halbautomatische Mustersuche im Data-Warehouse<br />

– von besonderem Interesse: Datenausreißer<br />

Techniken<br />

Data-Warehouse<br />

� Erstellung einer Klassifikation der Daten (z. B. Autoversicherungsklassen)<br />

– Klassen sind vorgegeben<br />

– Gesucht sind die Kriterien für eine Klassifizierung (mittels einer Testmenge)<br />

� Auffinden von Assoziationsregeln der Form X�Y – X und Y sind typischerweise Produkte, die gemeinsam in Transaktionen auftreten.<br />

– Konfidenz:<br />

rel. Häufigkeit der Transaktionen, die bereits X und zusätzlich noch Y enthalten.<br />

– Support:<br />

rel. Häufigkeit der Transaktionen, bei denen sowohl X als auch Y vorkommt.<br />

� Visual Data Mining<br />

Seite 373


10.4 Datenmodellierung<br />

� Transformation des mehrdimensionalen Datenmodells in ein ER-Diagramm<br />

ZID<br />

Tag<br />

Woche<br />

Monat<br />

Zeit<br />

PID<br />

Name<br />

Gruppe<br />

Produkt<br />

Verkauf<br />

Stückzahl<br />

Umsatz<br />

Geschäft<br />

Data-Warehouse<br />

GID<br />

Geschäft<br />

Region<br />

Land<br />

Seite 374


Definition<br />

Star-Schema<br />

Data-Warehouse<br />

Ein Star-Schema besteht aus einer Menge von Relationen D1 ,…,Dn , F mit folgenden<br />

Eigenschaften:<br />

1. Jede Relation Di modelliert eine Dimension des Datenwürfels. Zusätzlich zu den<br />

Attributen der Dimension bekommt Di einen künstlichen Primärschlüssel di zugeordnet. Di wird dann auch als Dimensionsrelation bezeichnet.<br />

2. Die Relation F verbindet die Dimensionen miteinander, indem die Fremdschlüssel der<br />

Dimensionsrelation (d. h. d 1 ,…,d n ) und die entsprechenden Messgrößen als Attribute<br />

umgesetzt werden. Diese Relation wird dann auch als Faktenrelation bezeichnet.<br />

Bemerkungen:<br />

� Das Star-Schema (genauer die Dimensionsrelationen) liegen nicht in dritter Normalform<br />

vor.<br />

Seite 375


Snowflake-Schema<br />

Data-Warehouse<br />

� Werden die Dimensionsrelationen des Star-Schemas in Normalform gebracht, so entsteht<br />

das Snowflake-Schema<br />

Jahr_ID<br />

Jahr<br />

Land_ID<br />

Land<br />

Quartal_ID<br />

Quartal<br />

Jahr_ID<br />

Region_ID<br />

Region<br />

Land_ID<br />

Monat_ID<br />

Monat<br />

Quartal_ID<br />

GID<br />

Geschäft<br />

Region_ID<br />

ZID<br />

Tag<br />

Monat_ID<br />

PID<br />

GID<br />

ZID<br />

Umsatz<br />

Stückzahl<br />

Faktenrelation<br />

Seite 376


Beobachtung<br />

� Die Faktenrelation ist im Vergleich zu den Dimensionsrelationen sehr groß.<br />

Leistungsbeurteilung<br />

Data-Warehouse<br />

� Keine Redundanz beim Snowflake-Schema.<br />

– Wird der Name einer Produktgruppe geändert, so ist im Snowflake-Schema nur ein<br />

Datensatz, im Star-Schema i. a. mehrere Datensätze, von der Änderung betr<strong>of</strong>fen.<br />

– Das Snowflake-Schema benötigt i. a. weniger Speicherplatz (zusätzlich müssen aber<br />

die künstlichen Schlüssel gespeichert werden).<br />

– Die Redundanz besitzt aber auf Grund der obigen Beobachtung kaum eine<br />

praktische Relevanz.<br />

� Durch die Denormalisierung werden bei Anfragen im Star-Schema weniger Joins<br />

berechnet. Zudem kann der Join zwischen der Faktenrelation und seinen<br />

Dimensionsrelationen sehr effizient berechnet werden.<br />

Seite 377


Anforderungen<br />

Anfragen auf dem Star-Schema<br />

� Ausführung von Aggregationen auf Teilmengen im Würfel<br />

� Detailierungsgrad des Würfels soll beliebig einstellbar sein<br />

Allgemeine Form einer Anfrage<br />

Data-Warehouse<br />

select g1 ,…,gk , agg(f1 ), …, agg(fm )<br />

aggregierte Messgrößen<br />

from<br />

where<br />

D1 ,…,Dn , F<br />

<br />

Relationen des Star-Schemas<br />

and<br />

… and<br />

and<br />

D.d 1 = F.d 1<br />

…<br />

D.d n = F.d n<br />

group by g 1 , …,g k ;<br />

and<br />

Bedingung des<br />

Star-Joins<br />

Seite 378


Beispiel:<br />

Data-Warehouse<br />

Finde die Quartalsumsätze aller Geschäfte differenziert nach Ländern im Jahr 2006 für die<br />

Produktgruppe Kaffee.<br />

select PName, Land, Quartal, sum(Umsatz)<br />

from Produkt P, Geschäft G, Zeit Z, FaktenRel F<br />

where Jahr = 2006 and<br />

Produktgruppe = “Kaffee” and<br />

Z.ZID = F.ZID and<br />

P.PID = F.PID<br />

G.GID = F.GID<br />

and<br />

group by PName, Land, Quartal;<br />

Bemerkungen<br />

� Die spezielle Form des Joins (Anfrage) wird auch als Star-Join (Star-Anfrage)<br />

bezeichnet.<br />

� Die Messgrößen in der Faktentabelle können bereits aggregiert sein (z. B. auf einen Tag).<br />

Es ist z. B. nicht möglich, die Anzahl der Kunden am Tag x zu bestimmen, die Kaffee<br />

kauften (da ein Kunde mehrere Kaffeeprodukte gleichzeitig kaufen kann).<br />

Seite 379


10.5 SQL-Erweiterungen<br />

Data-Warehouse<br />

� Defizite bei SQL im Hinblick auf Anfragen im Data-Warehouse<br />

– einfache Gruppierungsanfragen müssen in mehrere SQL Anweisungen aufgespalten<br />

werden.<br />

Beispiel<br />

� Relation: Anrufe(VVWahl, VNummer, ZVWahl, ZNummer, Datum, Länge)<br />

Ein Tupel dieser Relation protokolliert ein Telefongespräch und registriert dabei die Telefonnummern<br />

des Anrufers (VVWahl, VNummer), die Nummer des Angerufenen<br />

(ZVWahl, ZNummer), das Datum und die Länge des Gesprächs.<br />

� Anfrage: Finde für jeden Kunden, das von ihm geführte längste Telefongespräch und die<br />

entsprechende Vorwahl.<br />

� Lösung in SQL in zwei Schritten<br />

create view Tmp as<br />

select VVWahl, VNummer, MaxL = max(Länge)<br />

from Anrufe<br />

group by VVWahl, VNummer;<br />

Seite 380


Data-Warehouse<br />

select t.VVWahl, t.VNummer, ZVWahl, Länge<br />

from Anrufe a, Tmp t<br />

where Länge = MaxL and<br />

a.VVWahl = t.VVWahl<br />

a.VNummer = t.VNummer;<br />

and<br />

Die Berechnung besteht aus einem Subselect (Erzeugung von Tmp) und einem Join<br />

zwischen Tmp und Anrufe.<br />

Erweiterungsvorschlag von SQL: Gruppierungsvariablen<br />

� Gruppierungsvariablen werden in der group-by Klausel definiert.<br />

� In einer zusätzlichen Klausel (suchthat-Klausel) kann der Bereich der<br />

Gruppierungsvariablen noch eingeschränkt werden.<br />

� In der select-Klausel können nun die Aggregatsoperationen auf die<br />

Gruppierungsvariablen angewendet werden.<br />

� Beispiel:<br />

select VVWahl, VNummer, R.ZVWahl, R.Länge<br />

from Anrufe<br />

group by VVWahl, VNummer: R<br />

suchthat R.Länge = max(Länge);<br />

Seite 381


� In der Terminologie des mehrdimensionalen Datenmodells entspricht die suchthat-<br />

Klausel einem Herausschneiden einer Scheibe aus einem Würfel.<br />

Noch eine Anfrage:<br />

Data-Warehouse<br />

� Gib für jeden Kunden, die durchschnittliche Länge der Telefongespräche mit der<br />

Vorwahl 069 und 089 (in einem Datensatz).<br />

� In Standard SQL müssen zwei Sub-Anfragen (in Form von Views) und ein Join zwischen<br />

den Views berechnet werden<br />

� Durch die Verwendung von Gruppenvariablen vereinfacht sich die Formulierung der<br />

Anfrage erheblich:<br />

select VVWahl, VNummer, avg(R.Länge), avg(S.Länge)<br />

from Anrufe<br />

group by VVWahl, VNummer: R, S<br />

suchthat R.ZVWahl = “069” and<br />

S.ZVWahl = “089”;<br />

Seite 382


Data-Cube Operator<br />

Data-Warehouse<br />

� n-dimensionale Generalisierung der Idee der Kreuztabellen<br />

– 0-dimensionale Data Cube ist ein Punkt<br />

– 1-dimensionale Data Cube ist eine Linie mit einem Punkt<br />

– 2-dimensionale Data Cube ist eine Kreuztabelle<br />

– 3-dimensionale Data Cube ist ein Würfel mit drei sich überschneidenden<br />

Kreuztabellen<br />

� Beispiel<br />

– Dimensionsrelationen: Zeit, Geschäft, Produkt und Faktenrelation Verkauf(Umsatz)<br />

Getränke<br />

Cappel<br />

Erlenr.<br />

Wehrda<br />

Tee<br />

Kaffee<br />

Saft<br />

Bier<br />

1. Quart.<br />

2. Quart.<br />

3. Quart.<br />

4. Quart.<br />

C<br />

E<br />

W<br />

T K S B<br />

Summe Summe<br />

Summe<br />

Summe<br />

Geschäft<br />

Seite 383


Darstellung in einer Relation<br />

Geschäft Produkt Zeit Umsatz<br />

NULL NULL NULL 10000<br />

Cappel NULL NULL 3000<br />

Erlenr. NULL NULL 2000<br />

Wehrda NULL NULL 5000<br />

NULL Bier NULL 8000<br />

NULL Saft NULL 1500<br />

NULL Kaffee NULL 300<br />

NULL Tee NULL 200<br />

NULL NULL 1. Quart. 1000<br />

NULL NULL 2. Quart. 5000<br />

NULL NULL 3. Quart. 3000<br />

NULL NULL 4. Quart 1000<br />

Cappel Bier NULL 2500<br />

Wehrda Bier NULL 4000<br />

Erlenr. Bier NULL 1500<br />

... ... ... ...<br />

Erweiterung von group-by<br />

� Verwendung des Cube-Schlüsselworts<br />

Beispiel<br />

Data-Warehouse<br />

select g.Name, z.Quartal, p.Produkt, v.Umsatz<br />

from Geschäft g, Zeit z, Produkt p, Verkauf v<br />

where z.ZID = v.ZIDand p.PID = v.PID<br />

and g.GID = v.GID and<br />

p.Produktgruppe = “Getränke” and<br />

z.Jahr = 2005 and<br />

g.Region = “Marburg”<br />

group by cube (g.Name, z.Quartal, p.Produkt);<br />

Dieser Operator wurde auch in den Standard von<br />

SQL aufgenommen!<br />

Seite 384


Motivation<br />

10.6 Materialisieren von Aggregaten<br />

� Viele Anfragen: Gruppierung der Faktenrelation F<br />

select g1 , …,gk , agg(f)<br />

from F<br />

group by g1 ,…,gk ;<br />

Data-Warehouse<br />

Ist die Aggregationsoperation vorgegeben kann solch eine Anfrage allein über die Liste<br />

der Gruppierungsattribute beschrieben werden.<br />

Notation: (g1 ,…,gk )<br />

� Steigerung der Effizienz von Anfragen Q durch Materialisieren von Sichten V, die den<br />

oben definierten Anfragen entsprechen.<br />

– Für eine Anfrage Q und eine Sicht V definieren wir<br />

Q


Beispiel<br />

� Betrachten wir die Faktenrelation des TPC-D Benchmarks, die aus 3<br />

Dimensionsattributen Ware, Lieferant, Kunde besteht.<br />

� Es ergeben sich nun 23 Gruppierungsmöglichkeiten.<br />

– Diese Gruppierungsmöglichkeiten lassen sich als Knoten in einem Graphen<br />

veranschaulichen, wobei die Kanten durch die �-Relation gegeben sind.<br />

– Zusätzlich notieren wir die Anzahl der Tupel in den Sichten.<br />

(W, L, K) 6M<br />

(W, K) 6M (W, L) 0.8M (L, K) 6M<br />

(W) 0.2M (L) 0.01M (K) 0.1M<br />

() 1<br />

Data-Warehouse<br />

Seite 386


Problemstellung<br />

Data-Warehouse<br />

� Nehmen wir vereinfachend an, dass genau n Sichten materialisiert werden können und<br />

dass die Anfragen identisch zu den Sichten sind. Welche Sichten der Faktenrelation<br />

sollen materialisiert werden?<br />

� Die Kosten einer Anfrage werden dabei durch die Anzahl der Tupel von der Sicht v<br />

ausgedrückt (Cost(v)), die zur Anfragebearbeitung herangezogen wird.<br />

� Diese Fragestellung kann dahingehend verallgemeinert werden, dass statt der Anzahl der<br />

Sichten der verfügbare Speicherplatz vorgegeben wird.<br />

� Bereits diese stark vereinfachte Problemstellung ist NP-vollständig. Deshalb ist es<br />

gerechtfertigt, Heuristiken zur Lösung heranzuziehen.<br />

Folgerungen<br />

� Die oberste Sicht muss stets materialisiert sein, da sonst die entsprechende Anfrage nicht<br />

beantwortet werden kann.<br />

Seite 387


Greedy-Algorithmus<br />

Data-Warehouse<br />

� Im Folgenden betrachten wir einen iterativen Algorithmus zur näherungsweisen Lösung<br />

des oben genannten Problems.<br />

– Menge S enthält die bisher ausgewählten Sichten. S wird anfangs mit der obersten<br />

Sicht initialisiert.<br />

– Pro Schritt wird die Sicht mit dem höchsten Gewinn hinzugefügt.<br />

Algorithmus Gewinn(S, V)<br />

Eingabe: Menge S der ausgewählten Sichten, V eine noch nicht ausgewählte Sicht<br />

Ausgabe: Der Gewinn der Sicht V.<br />

1. FOREACH Sicht W mit W � V DO // W ist mittels V berechbar<br />

minCost := minX� S�W�X Cost�X�; // Betrachte Sichten aus S<br />

IF Cost(V) < minCost THEN // Bringt V etwas ?<br />

BW := minCost - Cost(V);<br />

ELSE<br />

BW := 0;<br />

�<br />

2. RETURN ; // Summe aller Gewinne von V<br />

W � V<br />

B W<br />

Seite 388


Zusammenfassung<br />

� In diesem Kapitel konnte nur kurz die Problemstellung angerissen werden.<br />

� Interessante Fragestellungen im Bereich des Data-Warehouse sind unter anderem:<br />

– Wartung und Aufrechterhaltung materialisierter Sichten<br />

– Datenintegration<br />

– effiziente Verfahren zum inkrementellen Laden eines Warehouse<br />

– schnelle Berechnung von Star-Joins<br />

– Indexstrukturen für Data-Warehouse (Zeit-Indexstrukturen)<br />

– Data Mining und Visualisierung<br />

� Organisation der Tabellen nicht mehr zeilen-, sondern spaltenweise<br />

– Optimale Unterstützung von eindimensionalen Aggregaten<br />

– Kompression von Spalten<br />

– Hoher Performancegewinn bei typischen Data-Warehouse-Benchmarks<br />

Data-Warehouse<br />

Seite 389

Hurra! Ihre Datei wurde hochgeladen und ist bereit für die Veröffentlichung.

Erfolgreich gespeichert!

Leider ist etwas schief gelaufen!