Bis zu welcher Normalform du gehst, ist letztendlich deine Entscheidung.
Der erste Schritt wäre:
Tabelle T1
ID | Name | Others |
1 | Foo | 1,25 |
2 | Bar | 3,86 |
3 | Baz | 0,98 |
Tabelle T2
Wenn zu jedem Typ zusätzliche Daten gehören, würde ich einen Schritt weiter gehen:
Tabelle T1
ID | Name | Others |
1 | Foo | 1,25 |
2 | Bar | 3,86 |
3 | Baz | 0,98 |
Tabelle T2
ID_T1 | Typ | Info |
101 | A | InfoA |
102 | B | InfoB |
103 | C | InfoC |
Tabelle T3
ID_T1 | ID_T2 |
1 | 101 |
2 | 101 |
2 | 102 |
3 | 101 |
3 | 102 |
3 | 103 |
Beim Lesen der Daten kommt man trotzdem mit einer Abfrage aus:
Code:
select t1.id, t1.name, t1.Others, t3.id_t2, t2.typ, t.info
from t1
left join t3 on t3.id_t1 = t1.id
left join t2 on t2.id = t3.id_t2
Delphi-Quellcode:
while not Query.EOF
do
begin
if (
not Assigned(MyObject))
or (MyObject.ID <>
Query.FieldByName('
ID').AsInteger)
then
begin
MyObject := TMyObject.Create;
MyObject.ID :=
Query.FieldByName('
ID').AsInteger;
MyObject.
Name :=
Query.FieldByName('
Name').AsString;
{...}
MyList.Add(MyObject);
end;
if Query.FieldByName('
ID_T2').AsInteger <> 0
then
begin
MyObjectTyp := TMyObjectTyp.Create;
MyObjectTyp.ID_T1 :=
Query.FieldByName('
ID').AsInteger;
MyObjectTyp.ID_T2 :=
Query.FieldByName('
ID_T2').AsInteger;
{...}
MyObject.Items.Add(MyObjectTyp);
end;
Query.Next;
end;
Der zeitliche Mehraufwand dürfte kaum spürbar sein.