Adressbuch

Werbung:
Konkret. Was ist jetzt an diesem generierten Skript "falsch"? Mir war nicht klar, dass man als Programmierer sich so intensiv mit einer Datenbank auseinandersetzen muss. Jetzt kommt meine naive Ansicht: Wozu gibt es DB-Entwickler ud wozu Programmierer? Heißt es nicht, das ein Schuster bei den Leisten bleiben solle? :-) Dafür sollten ja die Tools da sein, die einem Programmierer zum Beispiel die meiste Arbeit abnehmen. Sonst kann ich ja gleich ein DB-Entwickler werden.
 
Das mit der Geburt ist mein Fehler. Ich wollte die Zeile mit dem Datum formatieren. Und wieso die ID CHAR ist, mit einer Länge von 32? Weil ich mit meinem Programm eigene IDs erstelle. Ich generiere mit meinem Programm sogenannte UID oder auch GUID, und benutze diese als meine IDs. So hatte ich das in MS Access gehandhabt.

Wen ISAM Sondermüll ist, dann ist MYISAM wohl angesagt?
 
Manche Datenbanken können direkt selber UUID's:

PostgreSQL: Documentation: 9.4: pgcrypto

Code:
test=# create extension  pgcrypto;
CREATE EXTENSION
test=*# create table bla (id uuid default gen_random_uuid(), name text);
CREATE TABLE
test=*# insert into bla (name) values ('test');
INSERT 0 1
test=*# select * from bla ;
  id  | name
--------------------------------------+------
 0c422ce9-93f1-4ac8-be28-8f552dc4ca55 | test
(1 row)

ISAM / MyISAM ist hier wohl dasselbe. Unter MySQL ist InnoDB die Engine mit den geringsten Schmerzen.
 
Hier:
Änderungen an der eigentlichen Adressbuch-Tabelle nur als DDL... (Meine Paint Kenntnisse beschränken sich dann leider doch auf rote Linien ziehen :) )
Code:
Create Table adressbuch_tab
(
person_id Char(32) Not Null
,adressbuch_id Char(32) Not Null
,addressbuch_typ Boolean Not Null
,bundesland_id Char(32)
,bundesstaat_id Char(32)
,provinz_id Char(32)
,titel_id Char(32)
,anrede_id Char(32)
,kategorie_id Char(32)
,postfach_id Char(32)

,straße Varchar(250)
,hausnummer Int
,zusatz Varchar(100)
,postleitzahl Varchar(250)
,ort Varchar(250)

,Constraint addressbuch_tab_pk Primary Key (person_id, adressbuch_id, addressbuch_typ)
,Constraint addressbuch_tab_fk01 Foreign Key (bundesland_id) References bundesland_tab(bundesland_id)
,Constraint addressbuch_tab_fk02 Foreign Key (bundesstaat_id) References bundesstaat_tab(bundesstaat_id)
,Constraint addressbuch_tab_fk03 Foreign Key (provinz_id) References provinz_tab(provinz_id)
,Constraint addressbuch_tab_fk05 Foreign Key (titel_id) References titel_tab(ort_id)
,Constraint addressbuch_tab_fk06 Foreign Key (anrede_id) References anrede_tab(ort_id)
,Constraint addressbuch_tab_fk07 Foreign Key (kategorie_id) References kategorie_tab(ort_id)
,Constraint addressbuch_tab_fk08 Foreign Key (postfach_id) References postfach_tab(postfach_id)
);
Und hier dann noch dein Bild, angepasst mit allem was mMn entfallen kann / anders gehandhabt werden muss.

Edit:
Man sollte vielleicht auch noch erklären was man und warum man es geändert hat....

Die Änderung privat/geschäftlich sollte nach der ausführlichen Diskussion mit @akretschmer ja klar sein.
Weiterhin habe ich die Tabellen ort/postleitzahl und straße gelöscht. Der Grund ist recht simpel:
Das ganze funktionierend darzustellen würde bedeuten das man auch beziehungen innerhalb der einzelnen Relationen herstellen muss (eine Mozartstraße gibt es nunmal nicht in jedem Dorf/jeder Stadt) und das ganze das Datenvolumen explodieren lässt (mal ganz davon abgesehen das es jede Woche Umbenennungen gibt oder neue Straßen gebaut werden...). D.h. das sollte ein Freitextfeld bleiben. Genauso wie postleitzahl und ort... Solange du nicht gerade Postleitzahlen aller Orte der ganzen Welt zur Hand hast und importieren kannst, macht das auch recht wenig Sinn...

Edit Edit:
Die Spalte addressbuch_id muss dann natürlich aus der Tabelle "person" entfernt werden, diese Abhängigkeit bildest du ja hier ab.
Und wenn ich nicht so müde wäre, müsste ich auch nicht so oft editieren ... :oops:
 

Anhänge

  • Xaphus-Adressbuch_angepasst.jpg
    Xaphus-Adressbuch_angepasst.jpg
    444,5 KB · Aufrufe: 5
Zuletzt bearbeitet:
@Distrilec: Besten Dank für deine Mühe. Ich werde dir jetzt zwei Bilder zeigen. Im ersten Bild habe ich versucht deine Veränderungen 1:1 zu übernehmen. Das erste Bild können wir auch dazu nutzen, um zu überprüfen, ob ich dein DDL-Statement auch wirklich verstanden habe. Ich habe hier also versucht, das zu übernehmen was du meinst. Im zweiten Bild habe ich dann Änderungen vorgenommen. Dazu mehr werde ich später kommen. Zunächst das erste Bild:
Xarphus_1.jpg

Ich habe hier auch gleich mal die Beziehungen deutlicher gezeichnet, damit dies einfach ist nachzuvollziehen. Was mir hier gleich auf dem ersten Blick auffiel: Wie soll ich eine Person eintragen, die - sagen wir mal - neben einen Hauptwohnsitz noch zwei weitere Zweitwohnsitze hat? Ich versuche immer die reale Welt in einer Datenbank abzubilden. Also habe ich noch einmal darüber nachgedacht. Und dabei kam diese grafische Modellierung raus:
Xarphus_2.jpg
Was ist neu hinzugekommen? Ich habe mir die Freiheit erlaubt, und neben Bundesstaat, Provinz, und Bundesland auch noch Kanton hinzugefügt. Die Schweiz haben es gerne anders :)

Kurz zur Klärung, warum ich Ort, Straße und alles andere chronologisch wie ein Rattenschwanz nach hinten verlegt habe. Nun, ich denke wie folgt: zunächst einmal muss ich ja erst in einem Bundesland/Bundesstaat/Provinz/Kanton sein. Als nächstes kann ich mir dann einen Ort aussuchen. Habe ich mir einen Ort ausgesucht, erst dann folgen dann Straßen, Hausnummern, Postleitzahlen und Postfächer.

Dadurch, dass zwischen den eben vier genannten Einheiten eine n:m-Beziehung zum Adressbuch hergestellt wird, ist es möglich, dass die Person entweder mehrere Wohnsitze im selben Bundesland, in anderen Bundesländer, in anderen Bundesstaaten, in den selben Bundesstaaten etc. haben kann. Nun habe ich im weiteren Schritt eine n:m-Beziehung zwischen Ort und Bundesstaat(BS), Bundesland(BL), Provinz(P) und Kanton(K) hergestellt. Die fett markierten Abkürzungen der vier Einheiten habe ich dazu benutzt, damit die Zuordnungstabelle zwischen Ort und den vier Einheiten nicht ewig lang wird. Und ein jeder Ort (z.B. Hamburg) kann mehrere Postleitzahlen haben. Die Person kann ja in Hamburg-Zentrum sein Hauptwohnsitz haben, und irgendwo am Rande von Hamburg ein Zweitwohnsitz. Und die Postfächer ändern sich auch, genauso wie die Straßen sowie Postleitzahlen sich ändern.

Wobei ich gerade überlege, ob in einer Großstadt ein Straßenname mehrmals auftauchen kann? Also, dass der Straßenname in Hamburg auch in Berlin auftauchen kann, ist möglich. Die Mozartstraße gibt es ja nicht nur in Hamburg. Vermutlich gibt es diese Straße auch in Stuttgart?

Vielleicht habe ich auch deine Änderung nicht ganz verstanden. Ich versuche wirklich streng das reale Bild in einer Datenbank abzubilden. Deswegen liebe ich die Normalisierung so sehr. Auch wenn viele Konstellationen wenig Sinn ergeben, jedoch muss man sie dennoch nicht verwerfen oder?

Es ist ja durchaus möglich, dass eine sehr reiche Person neben einen Hauptwohnsitz mehrere Zweitwohnsitze hat. In Deutschland ist sowas durchaus legitim.

SZENARIO: Jetzt stellen wir uns einen Mann namens Hans vor. Er ist sehr reich. Muss sich um das Geld keine Gedanken machen. Hans' Mutter wohnt in Hamburg-Zentrum. So kann sie bequem einkaufen, und hat super Verbindungen zu den Ärzten. Sie ist sehr alt. Damit er in ihrer Nähe sein kann, wenn was ist, hat er sein Hauptwohnsitz am Rande von Hamburg angemeldet. Aber er findet Bayern total schön. Also hat er dort einen Zweitwohnsitz angemeldet. Aber sein Bruder wohnt in den USA. Die beiden verstehen sich super. Also hat er sich dort auch einen Wohnsitz angemeldet, und zwar in New York - die Stadt die niemals schläft. Und er führt eine Fernbeziehung. Seine hübsche Freundin lebt in Österreich, näherhin in Wien. Er mag es nicht in ihrer Wohnung zu übernachten und möchte seine Privatsphäre genießen. Also hat er sich dort ein Appartment gemietet, und läuft unter seinem Namen. Wir sehen, der Hans ist viel unterwegs. Und wenn jemand solch einen Freund hat, frage ich mich, wie ich es hätte in deiner Version unterbringen können? Du hast Recht, mein Szenario ist etwas weit hergeholt. Aber im Grunde wollte ich dir nur aufzeigen, dass dies durchaus möglich ist, und in der realen Welt nichts Verbotenes darstellt.
 
Zuletzt bearbeitet:
@akretschmer man lese eine Zeile weiter
Code:
,zusatz Varchar(100)
Das kann alles sein... einfach nur ein "a" aber auch ein "Gebäude B" oder "Stockwerk 32" :)

@Sophus Ohne das du lernst DDLs zu lesen wird das wohl nichts...

Ich habe in meiner Version dem Adressbuch noch die "person_id" hinzugefügt... Damit kann man so viele Adressen anlegen wie man will...
Kleines beispiel:
Code:
SQL> Select person_id, addressbuch_id, addressbuch_typ from addressbuch_tab;
PERSON_ID ADDRESSBUCH_ID ADDRESSBUCH_TYP
--------- -------------- ---------------
4321      01             F
4321      02             T
4321      03             F
4321      04             T
 
Zuletzt bearbeitet:
Also ist meine Version "komplett" falsch?

Aber noch einmal kurz zu diesem Adressbuch_Typ. Ich denke viel über mein Projekt nach. Und ich habe versucht, im Gesprochenen, das zu verstehen, aber irgendwie ist es bei mir noch nicht in Fleisch und Blut übergegangen. Du arbeitest hier mit zwei Werte, True und False. Vielleicht denke ich zu sehr in meiner Programmiersprache. Wenn irgendwas True ist, also Wahr, dann ist es privat, und wenn irgendwann False ist, also nicht wahr dann ist Geschäft? Und ab wann ist es beides, also Geschäft und Privat? Entschuldige, wenn ich das leidige Thema noch mal aufgreife, aber solange ich es noch nicht so innerlich verstanden habe, wird mich das gedanklich verfolgen.
 
Wie gut das ein Boolean nur theoretisch zwei Zustände hat.
In der Praxis sieht das anders aus -> Null/True/False (Also nicht definiert/wahr/falsch).
Das einzige was (zumindest in einer Datenbank) nur zwei Zustände hat ist eine Exception (entweder wird sie ausgelöst, oder eben nicht)

Könnte man jetzt dafür benutzen... Man kann aber auch einfach ein Textfeld (Länge 1) nehmen und dann die werte 'T', 'F' und wegen mir 'B' wählen... Oder eine Int-Spalte und dann die Wert 0, 1, 2...
Ich nenne es mal künstlerische Freiheit (ja, ein gutes Modell ist mMn Kunst...)

Also ist meine Version "komplett" falsch?
Um darauf einzugehen:
Natürlich ist dein Modell falsch... Oder sprichst du fließend Japanisch ohne auch nur ein Wort davon zu verstehen?
 
Wie gut das ein Boolean nur theoretisch zwei Zustände hat.
In der Praxis sieht das anders aus -> Null/True/False (Also nicht definiert/wahr/falsch).

Kann man mit NOT NULL verhindern. Das Problem ist (bei MySQL) ein anderes: es kennt IIRC BOOL nicht und simuliert das mit einem kleinen INT, der natürlich dann wieder mehr Zustände haben kann.
 
@Distrilec: Das mit dem japanischen Beispiel habe ich nicht verstanden. Aber das mein Modell falsch sei, das hätte gereicht. Das verstehe ich :cool: Aber zu den Werten. Irgendwie bist du leider immer noch nicht darauf eingegangen. Ich versuche Etwas im Gesprochenen zu verstehen. So lerne ich zum Beispiel Programmiersprachen. Ich "plappere" vor mich hin, was der Quelltext im Einzelnen macht. Ich versuche das wie ein Buch zu lesen. Und wenn ich das irgendwann problemlos hinkriege, dann weiß ich, ich habe es kapiert. Jeder hat da seine eigene Strategie.

Wir haben hier also drei werte, entweder 0,1,2 oder T, F und B. Das heißt,sobald 0/T ist, dann ist es privat. Steht dort aber 1/F, dann ist es eher Geschäft, und zu guter letzt, wenn ich 2/B sehe, dann ist es beide, sowohl Privat als auch Geschäft?
 
So, ich habe nun Distrilecs Modell übernommen und es erweitert. Zunächst werde ich das grafische Modell zeigen, dazu etwas sagen, und zum Schluss werde ich die DDL-Statements zeigen, damit ihr es in eurer Datenbank probieren könnt. Zu den Statements. Ihr müsst eine Datenbank namens xarphus anlegen. Hier nun das Bild:
Adressbuch.png
Ich habe hier der Vollständkeitshalber die Person-Tabelle mit einbezogen. Werfen wir einen Blick auf die Verwaltungsbezirke wie Kanton (Schweiz), Bundesland (Deutschland), Provinz (Italien), Grafschaft (England) und Bundesstaat (USA). Ich frage mich, ob es nicht besser wäre, all diese Bezirke in eine Tabelle unterzubringen?

Hinzu kam: E-Mail-Adresse-Tabelle. Hier benutze ich die Mail-Adresse also Primärschlüssel. Hier sah ich keinen Grund eine künstliche ID zu erstellen. Dann kam die Internet-Adresse-Tabelle hinzu. Auch hier benutze ich die Internet-Adresse als Primärschlüssel. Als nächstest kam die NachrichtSofortVersand-Tabelle hinzu. Klingt ein bisschen seltsam. Dahinter verbirgt sich einfach diese Instant-Messanger wie ICQ, Skype, AIM etc. In dieser Tabelle ist die Spalte Anbieter zu sehen. Mit Anbieter sind eben diese Messanger-Arten gemeint. Und zum Schluss (und hier kam ich etwas ins Straucheln) kam die Nummer-Tabelle hinzu. Ich wollte nicht für jedes Kommunikationsmedium eine Tabelle erstellen. Das heißt, Fax, Telefon, Mobiltelefon, Pager werden hier in einer Tabelle untergebracht. In dieser Tabelle ist die Spalte Gerät zu sehen. Mit Gerät meine ich hier wie Mobiltelefon, Telefon, Pager, Fax etc. Und die Nummern setzten sich ja aus bestimmten Bestandteilen zusammen. Zunächst aus einer Ländervorwahl, dann aus einer Vorwahl und zum Schluss aus einer Rufnummer.

Da dieses Forum keine *.sql-Dateien akzeptiert, habe ich die Datei in *.txt-Datei umgewandelt. Ich hoffe, dass es trotzdem funktioniert.
 

Anhänge

Werbung:
Das mit dem japanischen Beispiel habe ich nicht verstanden.
Man entscheidet nicht einfach so in einer Datenbank zu modellieren (oder Japanisch zu sprechen)... Man muss den Grundsatz, wenn man so will die Grammatik und die Vokabeln kennen.
Ansonsten "plappert" man nur sinnlosen Kram vor sich hin und die "Japaner" (wir DBAs / DB-Entwickler) verstehen ja doch nicht was du eigentlich willst ;)

Ich versuche Etwas im Gesprochenen zu verstehen. So lerne ich zum Beispiel Programmiersprachen. Ich "plappere" vor mich hin, was der Quelltext im Einzelnen macht.
Und genau das wird bei SQL (da sind wir ja noch nicht mal angekommen) nicht funktionieren... Weil es Funktionen gibt, die die Daten in einem Maße verändern, dass andere Personen (z.B. Tom Kyte von Oracle) ganze Kapitel eines Buches damit verbracht haben eine solcher Funktionen zu erklären.
Eine relationale Datenbank hat absolut nichts mit objektorientiertem Programmieren zu tun. Du arbeitest nie mit einem Objekt, sondern immer mit allem auf einmal.

Zunächst werde ich das grafische Modell zeigen, dazu etwas sagen, und zum Schluss werde ich die DDL-Statements zeigen, damit ihr es in eurer Datenbank probieren könnt.
Wenigstens lernst du schnell dazu... :)

Die Tabellen "E-Mail-Adresse", "Internet-Adressen", "Nummern", "Vorwahl" und "Ländervorwahl" sollten wieder Freitextfelder sein...
Das hat folgende Gründe:
1. Es wird programmtechnisch rechtschwer alle diese Abhängigkeiten darzustellen. Also das bei neuanlage erste die Telefonnummer angelegt werden muss, dann die Email Adresse und dann die Internetadresse und erst dann kannst du das eigentliche Adressbuch in der Datenbank einpflegen.
2. Es macht keinen Sinn so etwas "vorzugeben". Das sind Werte die sich recht häufig ändern werden... Also sollen das die User gefälligst auch selbst ändern :)
3. Eine Tabelle aus definitiv einzigartigen Werten braucht man nicht, der Wert ist in der Tabelle "Adressbuch" sowieso vorhanden... Also warum noch einmal eine extra Tabelle die keine weiteren Informationen zu dem Schlüssel hält?

Die Tabelle "Vorwahl" ist sogar doppelt unnötig. Sie hält nur einen Satz definitiv einzigartiger Werte, die in der Tabelle "Land" sowieso vorhanden sein werden UND den Wert dazu noch einmal in der Tabelle "Addressbuch" die auch immer ein Land hält (und das Land hat ja bekanntlich auch die Länder-Vorwahl hinterlegt). Wenn du die Vorwahl unbedingt vorgeben willst, solltest du wirklich einfach über die Relation "Land" gehen... Aber wie gesagt, ein Freitextfeld ist hier sinnvoller.
 
Zurück
Oben