Bayer Bäume
Im folgenden werden mit Pointer (ptr) RAM-Zeiger und mit Vektoren (vek)
Dateizeiger (long-Werte) bezüglich Dateibeginn bezeichnet.
Die Funktionen zur indexsequentiellen Dateiverarbeitung unterscheiden
beim Suchschlüssel, der ein String sein muß, zwischen Groß- und
Kleinbuchstaben. (Der erfahrene Anwender kann als Key jedoch auch mit
allen anderen Datentypen arbeiten !). Die Funktionen bauen einen
Bayer-Baum auf, der in seiner Baumtiefe nur durch die Speicherkapazität
des Speichermediums begrenzt wird. Die Blockgrӧe eines Indexblocks
des Bayerbaums beträgt normalerweise 2 Kb, kann jedoch zusätzlich
vom Anwender der Funktionen verändert werden.
Isamopen
--------
Syntax : void *isamopen(char *datname,unsigned reclen,unsigned keylen)
Parameter: datname: Dateiname der Indexsequenziellen Datei
(auch Pfad, max 80 Zeichen)
reclen : Datensatzlänge inklusive key
keylen : Indexschlüssellänge
Rückgabe : Bei Erfolg: Isamdateihandle :
void *isamhdl, ein Pointer zur Aufnahme
des Isamdateihandle muß vereinbart werden.
Ansonsten : NULL
Funktion : Öffnet ein indexsequentielle Datei. Als Dateiname muß der
Name der Datendatei übergeben werden (Es kann auch ein ganzer
Pfad übergeben werden). Der Datendateiname muß die
Extension '.dat' besitzen ! Der Indexdateiname
wird erzeugt, er besitzt die Extension '.idx'.
Die Schlüsselänge (keylen) darf nicht größer sein
als die Datensatzlänge (reclen). 'Keylen' und 'Reclen'
dürfen nicht kleiner sein als ein Byte. Der Key darf
nicht länger als 255 Bytes sein. Wird eine
existierende Datei mit falscher Schlüssellänge und/oder
falscher Datensatzlänge eröffnet, so werden Schlüssellänge
und Datensatzlänge auf den richtgen Wert korrigiert.
Isamclose
---------
Syntax : long isamclose(void *isamhdl)
Parameter: isamhdl: Isamdateihandle; muß definiert sein (z.B in main())
Rückgabe : Bei Erfolg: Positiver Wert
Bei Fehler: NULL
Funktion : Schließt eine Indexsequentielle Datei
Isamdel
-------
Syntax : long isamdel(void *isamhdl,void* isamrec)
Parameter: isamhdl: Isamdateihandle; muß definiert sein (z. B in main() )
isamrec: Pointer auf Key des Satzes, der gelöscht werden soll
Rückgabe : Bei Erfolg: Positiver Wert
Bei Fehler: NULL (Datensatz nicht vorhanden)
Funktion : Löscht einen Datensatz. 'isamrec' ist ein Pointer auf einen
vom Anwender reservierten Speicherbereich an dem sich der
Suchschlüssel (String) des zu löschenden Datensatzes
befindet.
Isamread
--------
Syntax : long isamread(void *isamhdl,void *isamrec)
Parameter: isamhdl: Isamdateihandle (wird von Isamopen zurückgegeben)
isamrec: Pointer reservierten Speicherplatz für
Datensatz
Rückgabe : Bei Erfolg: Vektor (long-Wert); entspricht der Position
des Datensatzes in der Datendatei, relativ
zum Dateibeginn.
Bei Fehler: NULL, d.h. der Datensatz wurde nicht gefunden.
Funktion : Liest einen Datensatz aus einer indexsequentiellen Datei.
Isamrec ist ein Pointer auf den Suchschlüssel (string).
An der Position isamrec muß sich genügend Platz für einen
Datensatz befinden (mindestens reclen Bytes; siehe isamopen).
Bei Erfolg befindet sich der gelesene Datensatz an der
Position reclen (beginnend mit dem Key).
šber den zurückgegebenen Vektor kann der Datensatz
direkt mit isamdatput() verändert werden, jedoch darf sich
der Key dann nicht ändern. Soll der Key geändert werden
muß isamwrite() benutzt werden !
Isamwrite
---------
Syntax : long isamwrite(void *isamhdl,void *isamrec,int mode)
Parameter: isamhdl: Indexdateihandle
isamrec: Pointer auf reservierten Speicherplatz
mode : Bestimmt die Arbeitsweise der Funktion
Rückgabe: mode 1 : Den Vektor an der sich der Datensatz in der
Datendatei befindet multipliziert mit -1
==> negativer Wert
Bei Fehler : NULL
mode 2 : den Vektor an der der Datensatz in der Datendatei
gespeichert wurde.
==> positiver Wert
Bei Fehler : NULL
mode 3 : den Vektor an der Datensatz in der Datendatei
gespeichert wurde.
==> positiver Wert
Bei Fehler : NULL
Funktion : mode 1 : Speichert einen Datensatz in der Isamdatei.
Ist schon ein Datensatz mit dem in isamrec
angegebenen Key in der Isamdatei so wird
der negative Datendateivektor auf den Datensatz
in der Datendatei zurückgegeben.
Die Isamdatei bleibt unverändert.
mode 2 : Wird nach mode 1 ausgeführt wenn die Warnung
aus mode 1 ignoriert werden soll.
==> Rewrite
mode 3 : Speichert ein Datensatz in der Isamdatei.
Existiert schon ein Datensatz mit dem in isamrec
angegebenen Key so wird ein Rewirte durchgeführt.
Ist der Key noch nicht vorhanden, so wird
der Datensatz ganz normal neu angelegt.
Wichtig : Da isamwirte über den mode 1 und den mode 2 verfügt,
ist es nicht notwendig ein isamread() vor einem
isamwrite() auszuführen, um festzustellen ob schon
ein Datensatz mit dem aktuellen Key in der Datei
gespeichert ist.
Ist schon ein Datensatz mit dem Key, der in isamrec
angegeben ist, in der Isamdatei, so wird dies durch
Rückgabe des negativen Vektors auf den Datensatz in
der Datendatei angezeigt.
Dieser Vektor könnte z.B. für isamdatput() verwendet
werden, wie es auch in der Funktion isamwirte()
durchgeführt wird.
mode 3 ist kompatibel zu:
long isamwrite(void *isamhdl,void *isamrec)
von Version 1.00 und 1.01 (kein mode Parameter).
Isamseqread
-----------
Synatax : long isamseqread(void *isamhdl,void *isamrec, int mode)
Parameter: isamhdl: Isamdateihandle
isamrec: Pointer auf freien Speicherbereich
mode : bestimmt die Arbeitsweise der Funktion isamseqread
Rückgabe : mode 1 : NULL: - der Key, der sich an der Adresse
isamrec befindet, größer ist, als
der größte Key der Indexdatei.
- die Indexdatei leer ist.
- nicht genug freier RAM-Speicher
Sonst: 1
mode 2 : NULL: - kein Datensatz mehr gefunden wurde,
also der größte Datensatz der Datei
schon ausgelesen wurde.
- die sequentielle Verarbeitung nicht
initialisiert (mode 1 oder 3) wurde.
Sonst: Vektor auf Position an der sich der
Datensatz in der Datendatei befindet
(immer > 0).
mode 3 : NULL: wenn der Key der sich an der Adresse
isamrec befindet größer ist als der
größte Key der Indexdatei.
Sonst: Vektor auf Position, an der sich der
entsprechende Datensatz in der
Datendatei befindet (immer > 0).
Funktion : mode 1 : Positioniert Pointer zur sequentiellen Verarbeitung
(Start-Anweisung). Muss vor dem ersten sequentiellen
Auslesen aus der Datei ausgeführt werden. Dazu muß
sich der Key, auf den positioniert werden soll, an
der Adresse isamrec befinden. Ist kein Datensatz mit
diesem Key vorhanden, so wird der Pointer auf den
Datensatz mit nächst größerem Key positioniert.
mode 2 : Liest den nächsten Datensatz. Der Datensatz
befindet sich dann, beginnend mit dem Key,
ab der Adresse isamrec. Wenn noch kein Datensatz
sequentiell gelesen wurde, wird der Datensatz gelesen
auf den mit mode 1 positioniert wurde.
mode 3 : Führt mode 1 und mode 2 aus.
Isamseqread
-----------
Wichtig : Ab der Adresse isamrec muß freier Speicherplatz für einen
Datensatz vorhanden sein (mindestens 'reclen' Bytes;
siehe auch isamopen()!). Wurde der größte Datensatz der
ISAM-Datei einmal ausgelesen, so wird der
Sequentielldateivektor gelöscht, d.h. vor dem nächsten
sequentiellen Verarbeiten muß erst wieder mit mode 1
oder mode 3 initialisiert werden. Während der sequentiellen
Verarbeitung kann jederzeit mit mode 2 oder mode 3
neu initialisiert werden.
Die Indexdateien können gleichzeitig sequentiell als auch
indexsequentiell bearbeitet werden.
Die sequentielle Verarbeitung erfolgt ab der Position
der Datei, an der zuletzt sequentiell gearbeitet
wurde (auch wenn zwischendurch indexsequentiell
verarbeitet wurde).
Die bei isamopen() angegebene Keylen ist mitentscheidend
für die Reihenfolge des sequentiellen Auslesens, d.h.,
die bis zur Keylen, am Anfang eines Satzes, gespeicherten
Bytes (entspricht dem Key) werden ASCII-lexikografisch
behandelt. Vorsicht wenn der Key z.B ein integer usw. ist,
Da bei Zahlen zuerst die Niederwertigen Bytes gespeichert
werden (Konvertierung in strings und strings als Key nehmen
für isamopen)
Bei mode 2 und mode 3 wird nach Rückgabe des Vektors auf
den nächsten Datensatz für das nächste Ausführen von
isamseqread() weitergeschaltet.
Der bei mode 2 und mode 3 zurückgegebene Vektor
kann zum direkten Verändern des Datensatzes in der
Datendatei mit isamdatput() eingesetzt werden.
isamdatget() braucht nicht mehr eingesetzt zu werden,
da sich der Datensatz schon an der Adresse
isamrec befindet. Wenn mit isamdatput() gearbeitet wird,
darf der Key nicht verändert werden. Wird der Key
verändert, so muß isamwrite() benutzt werden !
Isamcrunch
----------
Syntax : long isamcrunch(char *datname)
Parameter: datname: Datendateiname der zu "crunchenden" ISAM-Datei
(auch Pfad; Extension muß '.dat' sein ! - max 80 Zeichen)
Rückgabe : Bei Erfolg: NULL
Bei Fehler: 1 : Allgemeiner Fehler
2 : Fehler bei isammake()
Funktion : Cruncht eine Indexsequentielle Datei. Die Datei (Indexdatei
und Datendatei) darf nicht schreibgeschützt und nicht
durch 'isamopen()' geöffnet sein. Die Funktion Isamcruch
repariert die Dateien gleichzeitig. Isamcruch
funktioniert auch, wenn die Indexdatei defekt oder nicht
mehr vorhanden ist ! Die Funktion 'isammake()' wird von
'isamcrunch()' aufgerufen.
Anwendungsmöglichkeit: wenn eine ISAM-Datei trotz relativ
geringer Datensatzanzahl viel
Speicher beansprucht.
Speichereffizienz: kann durch das Verhältnis Datensatzlänge
zum Speicherplatzbedarf (-für Datendatei)
bzw. Keylänge zu Anzahl Indexstufen unter
Berücksichtigung der Indexblockgröße
(-für Indexdatei) bestimmt werden.
Wichtig : Es ist empfehlenswert vorher eine Sicherheitskopie der
Datei zu erstellen. Sowohl von der Indexdatei (Endung 'IDX'),
als auch von der Datendatei (Endung '. DAT') !
Isammake
-----------
Syntax : long isammake(char *srcname,char* destname, unsigned reclen,
unsigned keylen, long start)
Parameter: srcname : Dateiname der sequentiellen Datei (auch Pfad,
- max 80 Zeichen)
destname: Name der Indexdatei die erzeugt werden soll
(auch Pfad; Extension muß '.dat' sein !
- max 80 Zeichen)
reclen : Datensatzlänge
keylen : Schlüssellänge
start : Position relativ zum Dateibeginn an der mit der
Erzeugung begonnen werden soll
Rückgabe : Bei Erfolg: NULL
Bei Fehler: 1 : Allgemeiner Fehler
2 : Es wurde über das Dateiende von 'srcname'
hinaus gelesen, d.h. letzter Datensatz wurde
möglicherweise nicht verarbeitet
Funktion : Erzeugt aus einer sequentiellen Datei mit einheitlicher
Datensatzlänge und einem Key am Anfang des Datensatzes
eine indexsequentielle Datei. Der Key muß ein String sein.
Wichtig : Die Erzeugung einer indexsequentiellen Datei aus
einer sequentiellen Datei funktioniert nur dann einwandfrei,
wenn die Schlüssel-Strings der sequentiellen Datei
eindeutig sind. Funktion bei Mehrfachauftreten des gleichen
Keys:Es werden nur die Daten des sequentiell zuletzt
verarbeiteten Datensatzes in die Indexdatei aufgenommen !
Die folgenden Funktionen werden von den vorher beschriebenen Funktionen
zur Speicherung und Verwaltung, sowie Korrektur der Daten benötigt.
Isamramsrch
-----------
Syntax : void *isamramsrch(void *isamhdl,void *isamrec)
Parameter: isamhdl: Isamdateihandle
isamrec: Pointer auf den Suchschlüssel
Rückgabe : NULL : wenn der sich momentam im RAM befindende Block
keinen Eintrag hat.
Pointer: a) auf Key, wenn Key gefunden wurde.
b) auf kleinsten Key im Indexblock, wenn der Suchkey
kleiner ist, als der kleinste eingetragene Key,
oder nur ein Key im Block eingetragen ist.
c) auf größten Key im Indexblock, wenn Key größer
ist, als der größte eingetragene Key.
Ansonsten: Pointer auf nächst größeren Key
Funktion : Bestimmt die Position eines Suchschlüssels in einem Block.
Der Block muß sich, beginnend mit den Blockverwaltungsdaten
an der Position 'isamhdl+ISAMHLPSIZE' befinden.
Wird von 'isamread()' benötigt, um B-Baum zu durchsuchen.
Isamdatfre
----------
Syntax : long isamdatfre(void *isamhdl)
Parameter: isamhdl: Isamdateihandle
Rückgabe : Vektor auf freien Speicherplatz für einen Datensatz.
Funktion : Bestimmt einen freien Speicherplatz für einen Datensatz.
Isamidxfre
----------
Syntax : long isamidxfre(void *isamhdl)
Parameter: isamhdl: Isamdateihandle
Rückgabe : Vektor auf freien Speicerplatz für einen Indexblock.
Funktion : Bestimmt einen freien Speicherplatz für einen Datensatz.
Isamdatget
----------
Syntax : int isamdatget(void *isamhdl,void *isamrec,long vektor)
Parameter: isamhdl: Isamdateihandle
isamrec: Pointer auf freien Speicherplatz für Datensatz
vektor : Vektor auf Position des Datensatzes in der Datei
Rückgabe : Bei Erfolg: Positiver Wert entspricht Anzahl der
gelesenen Zeichen.
Bei Fehler: -1
Funktion : Liest einen Datensatz aus der Datendatei. An der Position
'isamrec' muß mindestens reclen freier Speicherplatz sein !
Isamdatput
----------
Syntax : int isamdatput(void *isamhdl,void * isamrec,long vektor)
Parameter: isamhdl: Isamdateihandle
: isamrec: Pointer auf Datensatz (beginnen mit Key)
: vektor : Vektor auf Position an der Datensatz gespeichert
werden soll
Rückgabe : Bei Erfolg: Anzahl der geschriebenen Zeichen
Bei Fehler: -1
Funktion : Schreibt einen Datensatz.
Isamidxget
----------
Syntax : int isamidxget(void *isamhdl,long vektor)
Parameter: isamhdl: Isamdateihandle
vektor : Vektor auf Position an der sich der Indexblock
befindet
Rückgabe : Bei Erfolg: Anzahl der gelesenen Zeichen
Bei Fehler: -1
Funktion : Liest einen Indexblock an die Position isamhdl+ISAMHLPSIZE
Isamidxput
----------
Syntax : int isamidxput(void *isamhdl,void *blkptr,long vektor)
Parameter: isamhdl: Isamdateihandle
blkptr : Pointer auf Position an der sich der Block, beginnend
mit den Blockverwaltungsdaten, befindet
vektor : Vektor auf Position an die der Block geschrieben
werden soll
Rückgabe : Bei Erfolg: Anzahl der geschriebenen Zeichen
Bei Fehler: -1
Funktion : Speichert einen Indexblock
Isamblksplt
-----------
Syntax : int isamblksplt(void *isamhdl,long vektor)
Parameter: isamhdl: Isamdateihandle
vektor : Vektor auf Position des Blocks der gesplittet
werden muß
Rückgabe : Bei Erfolg: positiver Wert
Bei Fehler: NULL
Funktion : Splittet einen Indexblock. Ist in einem Indexblock kein Platz
für eine weitere Eintragung, so muß dieser Indexblock
geteilt (gesplittet) werden. Wird die Wurzel gesplittet,
so wird eine neü Wurzel angelegt (der Baum wird tiefer bzw.
höher). Eventuelle Korrekturen der Söhne werden durch die
Funktion isamvatvek durchgeführt (wird von isamblksplt
aufgerufen). Die eventuelle Korrektur der Väter des
betreffenden Blocks wird durch die Isamblksplt
selbst durchgeführt.
Isamvatvek
----------
Syntax : int isamvatvek(void *isamhdl,long vektor)
Parameter: isamhdl: Isamdateihandle
vektor : Vektor auf Position des Indexblocks dessen Söhne
korrigiert werden müssen
Rückgabe : Bei Erfolg: Positiver Wert
Bei Fehler: NULL
Funktion : Bei einem Blocksplitting wird die Hälfte eines Blocks an eine
physikalisch andere Position in der Datei kopiert. Da die
Vatervektoren der Söhne dieses Blocks noch auf die alte
Position zeigen, müssen diese Vatervektoren (blkvatvek)
korrigiert werden. Beim Splitting wird immer der niederwertige
Teil eines Blocks an eine andere Position gespeichert.