Tag auch
Ich schreibe mir grade eine eigene Tabellen Klasse mit der ich arbeiten möchte. Die Tabelle soll nicht unbedingt dazu geeignet sein, das ein Nutzer sie über eine GUI bedient, sondern eher, das ich damit intern in meinen Programmen rechnen oder einfach nur in Tabellenform Daten darstellen und analysieren kann.
Ich stellen hier mal eine sehr frühe Version meiner Klasse rein (es gibt z.B. im wesentlichen kaum Bereichsprüfungen und ein paar Funktionen fehlen noch, z.B. wenn ein Wert geändert wird, das auch die Sortierung/Indexierung aktualisiert wird), um von euch zu erfahren ob ich auf dem richtigen Weg liege, oder ich irgendwo etwas grundlegend verbessern/ändern könnte.
Mir ist klar das ich auch alternativ eine Datenbank verwenden könnte. Das ist aber nicht der Weg den ich gehen möchte.
Den kompletten Quellcode stelle ich als Anhang rein. Hier nur mal der Interfaceteil zum reinschnuppern:
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25: 26: 27: 28: 29: 30: 31: 32: 33: 34: 35: 36: 37: 38: 39: 40: 41: 42: 43: 44: 45: 46: 47: 48: 49: 50: 51: 52: 53: 54: 55: 56: 57: 58: 59: 60: 61: 62: 63: 64: 65: 66: 67: 68: 69: 70: 71: 72: 73: 74: 75: 76: 77: 78: 79: 80: 81: 82: 83: 84: 85: 86: 87: 88: 89: 90: 91: 92: 93: 94: 95: 96: 97: 98: 99: 100: 101: 102: 103: 104: 105: 106:
| unit uTabelle;
interface
uses Variants, Classes, Types;
type TTBLArrTabelle = array of array of Variant;
TTBLArrVariant = array of Variant;
TTBLZelle = Variant;
TTBLDatenTyp = (dtInteger, dtReal, dtDateTime, dtString, dtColor, dtBoolean);
TTBLSortierung = (sKeine, sAufsteigend, sAbsteigend);
TTBLSpalte = record Name: string; DatenTyp: TTBLDatenTyp; Sortierung: TTBLSortierung; Indexiert: Boolean; end;
TTBLArrSpalten = array of TTBLSpalte;
TTBLTabelle = class(TObject) private fTabelle: TTBLArrTabelle; fSpalten: TTBLArrSpalten; fIndizes: TList; function GetAnzahlSpalten: Integer; function GetSpalte(Index: Integer): TTBLSpalte; function GetAnzahlZeilen: Integer; function GetZelle(Zeile, Spalte: Integer): Variant; procedure SetZelle(Zeile, Spalte: Integer; const Value: Variant); procedure SetAnzahlZeilen(const Value: Integer); function HatWertKorrektenDatenTyp(const Wert: Variant; const Spalte: Integer): Boolean; overload; function HatWertKorrektenDatenTyp(const Wert: Variant; const DatenTyp: TTBLDatenTyp): Boolean; overload; procedure SortiereSpalte(const Spalte: Integer; const VonIndex, BisIndex: Integer; const Sortierung: TTBLSortierung); public constructor Create; destructor Destroy; override; property AnzahlSpalten: Integer read GetAnzahlSpalten; property AnzahlZeilen: Integer read GetAnzahlZeilen write SetAnzahlZeilen; property Spalte[Index: Integer]: TTBLSpalte read GetSpalte; property Zelle[Zeile, Spalte: Integer]: Variant read GetZelle write SetZelle; default; procedure SpalteUmbennenen(const Index: Integer; const NeuerName: string); procedure SpalteHinzufuegen(const Name: string; const DatenTyp: TTBLDatenTyp); procedure ZeileHinzufuegen(var Zeile: TTBLArrVariant); overload; procedure ZeileHinzufuegen; overload; procedure SpalteLoeschen(const Index: Integer); procedure ZeileLoeschen(const Index: Integer); procedure WerteZeile(const Index: Integer; var Zeile: TTBLArrVariant); procedure WerteSpalte(const Index: Integer; var Spalte: TTBLArrVariant); procedure Zuruecksetzen; procedure Sortieren(const Spalte: Integer; const Sortierung: TTBLSortierung); procedure Indexieren(const Spalte: Integer); procedure IndexLoeschen(const Spalte: Integer); function Suche(const NachWert: Variant; out Zeile, Spalte: Integer; const InSpalte: Integer = -1; const AbZeile: Integer = 0; const AbSpalte: Integer = 0): Boolean; end;
TTBLIndexWert = record Wert: Variant; Indizes: TIntegerDynArray; end;
TTBLArrIndexWert = array of TTBLIndexWert;
TTBLIndex = class(TObject) private fIndex: TTBLArrIndexWert; procedure WertHinzufuegen(const Wert: Variant); procedure WertLoeschen(const Index: Integer); procedure WertEinfuegen(const Index: Integer; const Wert: Variant); procedure SortiereWerte(var Werte: TTBLArrIndexWert; const VonIndex, BisIndex: Integer); procedure SortiereIndexArr(var Indizes: TIntegerDynArray; const VonIndex, BisIndex: Integer); procedure SortiereIndex(const WertIndex: Integer); procedure IndexHinzufuegen(const WertIndex: Integer; const NeuerIndex: Integer); procedure IndexLoeschen(const WertIndex: Integer; const IndexIndex: Integer); procedure IndexEinfuegen(const WertIndex, IndexIndex, NeuerIndex: Integer); function GetAnzahlWerte: Integer; function GetAnzahlIndizes(WertIndex: Integer): Integer; function GetWert(Index: Integer): Variant; function GetIndex(WertIndex, IndexIndex: Integer): Integer; procedure Zuruecksetzen; public constructor Create; destructor Destroy; override; property AnzahlWerte: Integer read GetAnzahlWerte; property AnzahlIndizes[WertIndex: Integer]: Integer read GetAnzahlIndizes; property Wert[Index: Integer]: Variant read GetWert; default; property Index[WertIndex, IndexIndex: Integer]: Integer read GetIndex; function SucheWert(const Wert: Variant): Integer; function SucheIndex(const WertIndex, Index: Integer): Integer; function Suche(const Wert: Variant; const AbIndex: Integer = 0): Integer; procedure SpalteIndexieren(var Tabelle: TTBLTabelle; const Spalte: Integer); end; |
Um die Klasse benutzen zu können erstellt ihr einfach eine Instanz der TTBLTabelle Klasse.
Delphi-Quelltext
1: 2: 3: 4: 5:
| var tbl: TTBLTabelle; begin tbl:= TTBLTabelle.Create; end; |
Um Spalten zu definieren benutzt die TTBLTabelle.SpalteHinzufuegen Methode. In diesem Beispiel wird eine Spalte mit Namen "zahl1" und dem Datentyp Integer erstellt.
Delphi-Quelltext
1:
| tbl.SpalteHinzufuegen('zahl1', dtInteger); |
Um eine Zeile hinzuzufügen benutzt die TTBLTabelle.ZeileHinzufuegen Methode oder setzt entsprechend die Eigenschaft TTBLTabelle.AnzahlZeilen auf den richtigen Wert.
Delphi-Quelltext
1: 2: 3:
| tbl.ZeileHinzufuegen; tbl.AnzahlZeilen:= 5; |
Im die Tabelle mit Inhalt zu füllen benutzt die TTBLTabelle.Zelle Eigenschaft. Sie erwartet als Parameter die Zeile und Spalte. In dem Beispiel wird die Zeile 5 und Spalte 6 dem Wert 42 zugeweisen.
Delphi-Quelltext
Außerdem können Spalten Sortiert und Indexiert werden (In späteren Versionen kann man auch über mehrere Spalten sortieren). Der Einfachheit halber können derzeit nur Integer Spalten Indexiert werden (dafür aber mehrere, das Indexieren von andern Datentypen steht auf der ToDo Liste).
Um einen Wert zu Suchen benutzt die TTBLTabelle.Suche Methode. In dem Beispiel wird die Zahl 99 gesucht.
Delphi-Quelltext
1: 2: 3: 4: 5:
| var zeile, spalte: Integer; begin tbl.Suche(99, zeile, spalte, -1, 0, 0); end; |
Die Funktion liefert True zurück wenn die Suche erfolgreich war. In den Variablen zeile und spalte steht dann die Fundstelle. Um eine "Weitersuchen" Funktion zu realisieren kann in den letzten beiden Parametern angegeben werden, wo die nächste Suche beginnen soll. Die "-1" gibt an, das in allen Spalten gesucht werden soll. Soll nur in einer Spalte gesucht werden, könnt ihr hier den Index der Spalte angeben.
Die Suche berücksichtig indexierte oder sortierte Spalten und benutzt dafür optimierte Suchmethoden (Indexsuche und Binäresuche).
Ich freue mich auf euer Feedback.
Danke!
mfg
cbs