OptiVec logo 

VectorLib



Index:

OptiVec Home
MatrixLib
CMATH
Download
Bestellung / Registrierung
Update
Support

VectorLib


5. Fehlerbehandlung

5.1 Allgemeines
5.2 Ganzzahl-Fehler
5.3 Fließkomma-Fehler
5.3.1 C/C++-spezifisch
5.3.2 Pascal/Delphi-spezifisch
5.3.3 Fehlerarten (sowohl C/C++ als auch Pascal/Delphi)
5.4 Die Behandlung nicht-normalisierter Zahlen
5.5 Fortgeschrittene Fehlerbehandlung: Meldungen in eine Datei schreiben
5.6 OptiVec-Fehlermeldungen

5.1 Allgemeines

Es gibt grundsätzlich zwei Arten von Fehlerbehandlung: Durch die Hardware oder durch die Software. Um einen unkontrollierten Absturz zu vermeiden, ist es immer wünschenswert, drohende Fehler durch die Software abzufangen, bevor sie Unheil anrichten können. Alle Hochsprachen unterstützen diese Software-Fehlerbehandlung bis zu einem gewissen Grad an Perfektion. Innerhalb der sehr strikt definierten OptiVec-Funktionen läßt sich häufig eine noch effizientere Fehlerbehandlung durchführen als sie einem Compiler für "normalen" Programmcode möglich ist. Auch hier sind allerdings Grenzen gesetzt, insbesondere für den Überlauf-Schutz innerhalb der extended-, teilweise auch der double-Versionen von OptiVec-Funktionen. Der Programmierer sollte generell darauf achten, daß konstante Paramater bei der Übergabe an Funktionen sicherheitshalber nicht größer als 1.E32 für float / Single, 1.E150 für double und 1.E2000 für extended sind.

In den "erweiterten" Versionen aller extended-genauen Funktionen (also denen mit den Präfixen VEx_ und VCEx_; z.B. VEx_exp) wird generell kein Überlauf-Schutz für die Berechnung des Zwischenergebnisses A*Xi+B gewährt, sondern nur für den Kern der Funktion selbst und für die abschließende Multiplikation mit dem Skalierungsfaktor C.

Wie üblich, werden Fehler durch Ausgabe einer Meldung angezeigt. Eine Folge identischer Fehler innerhalb ein- und derselben OptiVec-Funktion führt dabei immer nur zu einer einzigen Meldung. Nachfolgende identische Meldungen werden unterdrückt.

Zwischen Fließkomma- und Ganzzahlen besteht ein grundsätzlicher Unterschied bezüglich OVERFLOW- und DOMAIN- Fehlern: Für Fließkommazahlen sind dies ernst zu nehmende (OVERFLOW) bzw. meist zum Abbruch führende (DOMAIN) Fehler. Demgegenüber wird für Ganzzahlen eine implizite modulo-2n-Arithmetik verwendet, bei der diese "Fehler" gar nicht als solche betrachtet werden. Im Gegenteil: Häufig wird sogar der Überlauf als schnelles Mittel der modulo-Division ausgenutzt. In den folgenden beiden Abschnitten wird die Fehlerbehandlung von Fließkomma- und Ganzzahlen detailliert dargestellt.

Zurück zum VectorLib-Inhaltsverzeichnis     OptiVec Home

5.2 Ganzzahl-Fehler

Die einzige Operation, die bei ganzen Zahlen immer ein Fehler ist, ist die Division durch 0, die zu einem ZERODIVIDE-Fehler führt. Überlauf- und Bereichs-Fehler, also INTEGER OVERFLOW und INTEGER DOMAIN (letztere entstehen z.B. beim Zuweisen einer negativen Zahl zu einem vorzeichenlosen Typ), werden schlicht ignoriert bzw. im Sinne der erwähnten impliziten modulo-2n-Arithmetik um-interpretiert. Für Fälle, in denen dies nicht erwünscht ist, bietet VectorLib neben der Normalversion aller Integer-Funktionen eine weitere Version mit der Möglichkeit, diese Fehler abzufangen und eine Fehlermeldung auszugeben, gegebenenfalls auch das Programm abzubrechen.

Nur 32-bit-Versionen (also nicht für 64-bit):
Alle Funktionen, in denen INTEGER OVERFLOW (z.B. in VI_rampVI_mulV, etc.) oder INTEGER DOMAIN-Fehler (z.B. in V_ItoU für negative X-Werte) auftreten können, existieren in zwei Varianten: Die Normalversion wendet implizite modulo-2n-Arithmetik an und wandelt vorzeichenbehaftete und vorzeichenlose Typen gemäß ihrem Bitmuster ineinander um. Für die 16-bit- und 32-bit-Ganzzahltypen (nicht aber für 8-bit und 64-bit) gibt es eine zweite Version, die zwar auch modulo-2n-Arithmetik anwendet, Fehler aber detektiert. Diese zweite Variante wird durch den Buchstaben "o" (für "OVERFLOW-Detektion") im Präfix angegeben: VIo_,  VSIo_,  VULo_, usw. Für die Ganzzahl-Datentypumwandlungsfunktionen wird das Präfix V_ zu Vo_ erweitert. Was im Falle eines Fehlers zu geschehen hat, wird durch einen Aufruf der Funktion V_setIntErrorHandling festgelegt. Diese benötigt ein Argument des Typs V_ihand (definiert in <VecLib.h> bzw. in der Unit VecLib), das drei verschiedene Werte annehmen kann:
 

ierrNoteAusgabe einer Fehlermeldung und Fortsetzung des Programmes
ierrAbortAusgabe einer Fehlermeldung und Abbruch des Programmes
ierrIgnore Fehler ignorieren; mit dieser Option läßt sich die Fehlerbehandlung für einzelne Stellen im Programm wieder ausschalten.

Obwohl ein Aufruf von
V_setIntErrorHandling( ierrIgnore );
im Prinzip verwedet werden kann, um die Fehlerbehandlung auszuschalten, ist es stets besser, einfach die Normalwersion (Präfix VI_) anstelle der VIo_-Version mit überbrückter Fehlerbehandlung zu verwenden, da die Normalversion immer um ein Vielfaches schneller ist.

nur C/C++:
Um die Überlauf-abfangede Variante nicht nur für einzelne Funktionsaufrufe, sondern überall zu verwenden, ist der einfachste Weg, die symbolische Konstante V_trapIntError im Programmkopf vor(!) Einschluß von <VecLib.h> zu definieren, z.B.
#define V_trapIntError 1
#include <VIstd.h>
#include <VImath.h>
.....
main() /* oder WinMain() oder OwlMain() */
{
  iVector I1, I2;
  I1 = VI_vector( 1000 ); I2 = VI_vector( 1000 );
  V_setIntErrorHandling( ierrNote );
  VI_ramp( I1, 1000, 0, 50 ); /* hier wird ein Überlauf auftreten! */
  V_setIntErrorHandling( ierrIgnore );
  VI_mulC( I2, I1, 1000, 5 );
    /* hier entsteht zwar eine ganze Serie von Überläufen, die aber alle ignoriert werden */
  ....
}

Zurück zum VectorLib-Inhaltsverzeichnis     OptiVec Home

5.3 Fließkomma-Fehler

5.3.1 C/C++-spezifisch

Die Behandlung von Fließkomma-Fehlern lehnt sich eng an die Behandlung in den mathematischen Funktionen von C/C++ an. Insbesondere gilt auch für die Funktionen von OptiVec, daß _matherr (in Borland C vor der Version 4.0: matherr, ohne den Unterstrich) und _matherrl der Dreh- und Angelpunkt der Fehlerbehandlung sind und vom Benutzer auf die jeweiligen Bedürfnisse zugeschnitten werden können. Dabi wird _matherr von den VF_,  VCF_,  VD_ und VCD_-Funktionen verwendet und _matherrl von den VE_ und VCE_- Funktionen (letzteres nur Borland C++, da Visual C++ 80-bit-IEEE-Zahlen nicht unterstützt).

Falls die Funktion, in der ein Fehler auftritt, ein reelles Argument enthält, wird nur der Parameter e->x definiert beim Aufruf von _matherr; e->y bleibt undefiniert. Nur falls zwei Argumente nötig sind (wie in VF_atan2 oder in VF_cotrpi), werden e->x und e->y zur Aufnahme dieser beiden Argumente benutzt. Bei komplexen Argumenten wird der Realteil (bzw. für Polarkoordinaten der Mag-Teil) in e->x übergeben und der Imaginärteil (bzw. der Zeigerwinkel) in e->y.

Zurück zum VectorLib-Inhaltsverzeichnis     OptiVec Home

5.3.2 Pascal/Delphi-spezifisch

Die in mathematischen Funktionen auftretenden Fehlerarten werden unten einzeln beschrieben. Wie OptiVec die einzelnen Fehlerarten behandelt, wird durch Aufruf von V_setFPErrorHandling vorgegeben. Die vorhandenen Optionen werden durch die vordefinierten Konstanten fperrXXX gesetzt, siehe V_setFPErrorHandling. Beim Aufruf von V_setFPErrorHandling sollten diese Konstanten mit dem OR-Operator verknüpft werden. Man beachte, daß dies nur die Behandlung von Fehlern beeinflußt, die innerhalb von OptiVec-Funktionen auftreten. Die zu Borland Pascal/Delphi gehörenden Standard-Funktionen bleiben hiervon unberührt.

Zurück zum VectorLib-Inhaltsverzeichnis     OptiVec Home

5.3.3 Fehlerarten (sowohl C/C++ als auch Pascal/Delphi)

Für jede Funktion werden die möglichen Fehlerarten, die abgefangen und behandelt werden, in der Beschreibung der jeweiligen Funktion aufgeführt. Alle von mathematischen ANSI C- oder Pascal/Delphi-Funktionen abgeleiteten VectorLib-Funktionen (also diejenigen, deren Deklaration sich in <V?math.h> bzw. den Units V?math findet) führen eine vollständige Fehlerbehandlung für jedes Vektorelement durch. Über diese Fehlerbehandlung "pro Element" hinaus wird mit Hilfe des Rückgabewertes angegeben, ob insgesamt irgendein Fehler auftrat oder nicht. Ein Rückgabewert von FALSE (0) bedeutet Fehlerfreiheit; Rückgabewerte von TRUE (ungleich 0) zeigen aufgetretene (und behandelte) Fehler an.

Bei der nun folgenden Beschreibung der einzelnen möglichen Fehler wird als "HUGE_VAL" der größte im jeweiligen Datentyp darstellbare Wert bezeichnet, also MAX_FLT,  MAX_DBL oder MAX_LDBL, je nach Typ. Ähnlich wird mit "TINY_VAL" der kleinste eben noch darstellbare Wert ungleich 0 bezeichnet. Dies ist nicht dasselbe wie MIN_VAL, welches der kleinste mit voller Genauigkeit darstellbare Wert ist.

  • DOMAIN-Fehler (Argument außerhalb des Bereiches, für den eine Funktion definiert ist) führen meist zum Resultat NAN ("not-a-number", die IEEE-Nicht-Zahl).
    In C/C++ wird empfohlen, _matherr und _matherrl so zu modifizieren, daß DOMAIN-Fehler zum Programm-Abbruch führen. Andernfalls führt die nächste Operation mit dem gerade zu einer NAN gemachten Vektorelement ohnehin höchstwahrscheinlich zu einem Absturz. Ein Beispiel für eine angepaßte _matherr-Funktion wird weiter unten gegeben. Alternativ kann auch der UNIX-Stil gewählt werden; vergleiche die Datei MATHERR.C, die normalerweise mit C-Compilern ausgeliefert wird.
    Für Pascal/Delphi empfehlen wir, die Standardeinstellung von V_FPErrorHandlingMode nicht zu verändern oder "fperrAbortDOMAIN" in alle eventuell geänderten Einstellungen mit einzubeziehen.
    N.B.: Die Pseudo-Zahlen INF und NAN sind nicht als Argumente für VectorLib-Funktionen zugelassen. Ihre Anwesenheit kann zu einem Programmabbruch durch einen Hardware-Interrupt führen.
  • SING-Fehler (Singularitäten, also explizite oder implizite Divisionen durch 0) werden als Extremfall des Überlaufs betrachtet (OVERFLOW-Fehler, s. unten). Das Ergebnis wird in den meisten Fällen auf ±HUGE_VAL gesetzt. Obwohl auch im Falle von SING-Fehlern ein Programm-Abbruch anzuraten ist, kann eine Fortsetzung doch unter Umständen noch zu sinnvollen Resultaten führen.
  • OVERFLOW (Überlauf) dürfte die am häufigsten vorkommende Sorte von Fließkomma-Fehlern sein. Das Resultat wird – je nach Vorzeichen – auf +HUGE_VAL oder -HUGE_VAL gesetzt. In vielen Fällen dürfte die Fortsetzung des Programmes noch zu brauchbaren Resultaten führen.
    Nur C/C++: Im Prinzip braucht man die hier genannten Resultate nicht zu akzeptieren, sondern kann sie modifizieren, indem man einen anderen Rückgabewert von _matherr definiert. Hiervon wird allerdings aus mehreren Gründen abgeraten: Das Vorzeichen des Resultates wird von der "Beschwerde führenden" Funktion häufig erst nach Rückkehr von _matherr gesetzt; der den Fehler verursachende x-Wert steht meist in Form von Xi, gelegentlich – bei den erweiterten Formen komplexer Funktionen – aber nur als Zwischenergebnis x' = Ax + B zur Verfügung. Man beachte außerdem, daß alle x-Werte an _matherr als doubles übergeben werden, auch in Fällen wie VF_tanrpi, wo die zum Fehler führenden Integers Pi und q in doubles umgewandelt und so als x and y an _matherr weitergereicht werden.
  • TLOSS-Fehler (totaler Genauigkeitsverlust) werden nur dann über _matherr abgewickelt, wenn sich hinter ihnen einer der schwereren oben genannten Fehler verbergen könnte.
    Beispielsweise ist der Cosecans als Kehrwert des Sinus für ganzzahlige Vielfache von p nicht definiert, so daß der "vollständig ungenaue" Wert auch zu einem SING- oder OVERFLOW-Fehler gehören könnte.
    Andererseits nimmt die Sinus-Funktion nur Werte zwischen -1 und +1 an für alle Argumente. Daher ziehen wir es vor, das "vollständig ungenaue" Resultat einer Sinus-Berechnung "stillschweigend" als 0.0 anzusehen und die OptiVec-Fehlerbehandlungsroutine nicht zu rufen (Borland C wählt NAN, die "Nicht-Zahl", als Resultat, was sicherlich noch weniger korrekt ist als die willkürliche Wahl von 0.0, denn das Ergebnis der Sinus-Funktion ist eben immer eine Zahl und keine Nicht-Zahl).
    Generell wird als Resultatim Falle von TLOSS-Fehlern der Mittelwert der Funktionswerte für Argumente +0.0 und -0.0 gewählt.
  • UNDERFLOW-Fehler (Unterlauf) werden nicht detektiert. Die Intel-Coprozessoren setzen das Resultat im Falle von UNDERFLOW-Fehlern zunächst auf nicht-normalisierte Zahlen (s. Kap. 5.4) und schließlich auf 0.0. Man wird kaum eine andere Behandlung wünschen können.
  • Wie alle (nicht-vektorisierten) mathematischen Funktionen von C/C++ und Pascal/Delphi detektieren auch OptiVec-Funktionen niemals PLOSS-Fehler (partieller Genauigkeitsverlust); Genauigkeitsprobleme werden schlicht ignoriert. Dies mag Mathematikern die Haare zu Berge stehen lassen, ist aber so üblich und ohne größeren Aufwand auch nicht zu ändern.

Zurück zum VectorLib-Inhaltsverzeichnis     OptiVec Home

5.4 Die Behandlung nicht-normalisierter Zahlen

Nicht-normalisierte Zahlen (engl.: denormals) sind sehr kleine Zahlen zwischen 0 und der kleinsten in voller Genauigkeit darstellbaren Zahl des jeweiligen Datentyps. Man mag das ihnen zugrundeliegende Prinzip am folgenden vereinfachten Beispiel verstehen:
1.175494E-38 ist die kleinste normalisierte float / Single, mit 7-stelliger Genauigkeit. Was geschieht, wenn diese Zahl durch, sagen wir, 1024 geteilt wird? Das Ergebnis kann nur als 0.001145E-38 dargestellt werden, das heißt, mit nur noch 4-stelliger Genauigkeit. Die ersten drei Stellen sind ja für führende Nullen verbraucht. Auf diese Weise "vermitteln" Denormals einen sanften Übergang zwischen sehr kleinen Zahlen und 0. Generell können sie als ganz gewöhnliche Zahlen behandelt werden.

Bei der Bildung des Kehrwertes allerdings folgt ein Überlauf, und hier wird die etwas akademische Unterscheidung zwischen SING- und OVERFLOW-Fehlern fallengelassen und ein SING-Fehler angezeigt, als ob es sich um eine Division um exakt 0 handelte.

Andererseits geben Denormals als Argumente von einigen Funktionen, beispielsweise log, völlig vernünftige Ergebnisse, während exakt 0 als Argument zu einem SING-Fehler führt. Leider behandeln die meisten Compiler auch für diese Funktionen Denormals als 0. Wir schließen uns dem nicht an und berechnen lieber das Ergebnis.

Zurück zum VectorLib-Inhaltsverzeichnis     OptiVec Home

5.5 Fortgeschrittene Fehlerbehandlung: Meldungen in eine Datei schreiben

Allgemein bieten die mit Compilern mitgelieferten Bibliotheken dem Programmierer keine sehr gute Kontrolle über die Art, wie Fehlermeldungen ausgegeben werden. In den meisten Fällen ist dies akzeptabel. Gelegentlich möchte man aber vielleicht die Meldungen lieber in eine Datei schreiben, um nach Abarbeitung des Programms in Ruhe studieren zu können, was schiefgegangen ist. Unter Windows kommt noch hinzu, daß für jeden Fehler eine Meldungs-Box erzeugt wird, auf die der Anwender zu reagieren hat, bevor die Ausführung fortgesetzt werden kann.

Man mag dies umgehen wollen. Eine einfache Lösung dieses Problems besteht in der Funktion V_setErrorEventFile. Diese Funktion benötigt als Argumente den Namen der gewünschten Ereignis-Datei ("Log-File") und einen Schalter, ScreenAndFile, der darüber entscheidet, ob Fehlermeldungen ausschließlich in die Datei (ScreenAndFile = FALSE (0)) oder außerdem noch auf dem Bildschirm (ScreenAndFile = TRUE (> 0)) auszugeben sind.

Beispiel:
V_setErrorEventFile( "MyLogFil.TXT", 0 );  /* C/C++ */
V_setErrorEventFile( 'MyLogFil.TXT', FALSE );  (* Pascal/Delphi *)

Hier werden alle folgenden Fehlermeldungen nur in das Log-File MyLogFil.TXT geschrieben, aber keine auf dem Bildschirm angezeigt. Die Standardeinstellung, d.h. Meldungsausgabe auf dem Bildschirm (unter Windows in MessageBoxen) wird durch V_closeErrorEventFile wiederhergestellt. Diese letztere Funktion hat keine Argumente und gibt auch nichts zurück.

Man beachte, daß die beschriebene Umleitung von Fehlermeldungen zunächst nur für Fehler gilt, die innerhalb von OptiVec-Funktionen auftreten. Es gibt aber in C/C++ die Möglichkeit, sie auch für alle anderen über _matherr und _matherrl behandelte Fehler auszunutzen. Hierzu muß die _matherr-Funktion so modifiziert werden, daß anstelle der Zeile
return 0;
(die einen ungelösten Fehler anzeigt) die Sequenz steht
V_noteError( e->name, e->type ); return 1;
Hierdurch wird die Ausgabe der Fehlermeldung durch die OptiVec-Funktion V_noteError übernommen, die jeweils prüft, ob ein Log-File definiert wurde, und die Ausgabe an die gewünschte Stelle leitet. Durch den Rückgabewert 1 von _matherr wird die "normale" Fehlermeldung der _matherr aufrufenden Funktion unterdrückt.

Eine Anwender-definierte Funktion _matherr (matherr – ohne Unterstich – für Borland C++ 3.0 und 3.1) könnte also etwa wie folgt aussehen:
#include <math.h>
int _matherr( struct exception *e) /* "_exception" für MSVC */
{
  if( (e->type == UNDERFLOW) || (e->type == TLOSS) ) ; /* ignorieren */
  else /* alle anderen Fehler zumindest mitteilen */
  {
    V_noteError( e->name, e->type );
    if (e->type == DOMAIN) exit(1); /* tödlich */
  }
  return 1;
}

(Wenn Sie _matherr ändern, vergessen Sie nicht, dieselben Änderungen auch für _matherrl durchzuführen, falls Sie mit Borland C++ arbeiten!)

Eine Möglichkeit, auch vom Auftreten der nicht zu einer Meldung führenden Fehler zu erfahren, wird durch die Rückgabewerte der mathematischen VectorLib-Funktionen geboten. Alle "stillen" TLOSS- ebenso wie die schwereren DOMAIN-, SING- und OVERFLOW-Fehler führen zu einem Rückgabewert von TRUE (ungleich 0). Man kann nach einer Reihe von Funktionsaufrufen testen, ob für alle Vektorelemente ein "sauberes" Resultat berechnet wurde, wie im folgenden C/C++-Beispiel:
unsigned ErrFlag;
...
/* Teil Trig1 */
ErrFlag=0; /* Flag zurücksetzen */
ErrFlag |= VF_sin( Y1, X1, sz );
ErrFlag |= VF_cos( Y2, X1, sz );
ErrFlag |= VF_atan2( Z1, Y1, Y2, sz );
if( ErrFlag ) V_printErrorMsg( "Fehler in Teil Trig1 aufgetreten!");
...

Wie in diesem Beispiel gezeigt, ist es besser, den Operator |= (Pascal/Delphi: "ErrFlag := ErrFlag or") zu verwenden anstelle von += (da in dem allerdings sehr seltenen Fall, daß sich die Rückgabewerte zu 65536 addieren, durch Überlauf der Ganzzahlvariablen 0 als scheinbar fehlerfreies Ergebnis erhalten würde). Selbst wenn man in C/C++ Addition der einzelnen Rückgabewerte wählte, könnte man doch auf diesem Wege nicht die Anzahl aufgetretener Fehler ermitteln, da der Rückgabewert im Fehlerfall eine nicht-spezifizierte Zahl ungleich 0 ist.

Zurück zum VectorLib-Inhaltsverzeichnis     OptiVec Home

5.6 OptiVec-Fehlermeldungen

Wie in jedem in C/C++ oder Pascal/Delphi geschriebenen Programm führen Fehler in den mathematischen Funktionen zu entsprechenden Meldungen, siehe Absatz 5.3.3.
Nicht nur in mathematischen Funktionen können freilich Fehler auftreten, sondern es gibt eine Reihe von Fehlern, die spezifisch für bestimmte Funktionen von OptiVec sind. Die durch sie erzeugten Meldungen werden in diesem Kapitel erläutert. Der in den Meldungen auftauchende Funktionsname ist nicht immer exakt derselbe, den Sie in Ihrem Programm geschrieben haben. So werden Sie anstelle des Präfixes VI_ entweder auf VSI_ oder VLI_ stoßen, je nach Speichermodell. Auch werden sich VFs_FFT oder VFl_FFT melden, wo Sie VF_FFT schrieben, wiederum abhängig vom Speichermodell. Der Grund für dieses Verhalten ist natürlich, daß viele Funktionen gemeinsamen Code benutzen und einige Namen als Synonyme für andere definiert sind.

 

(00) OptiVec/CMATH not installed correctly
(must use INSTALL.EXE !)
Nur in der Shareware-Version: Entweder führen Sie ein Programm, das OptiVec-Funktionen enthält, auf einem anderen Rechner aus als dem, wo Sie OptiVec installiert haben; die Weitergabe von Anwendungen, die OptiVec-Funktionen enthalten, ist aber nur mit der registrierten Vollversion möglich.
Oder Sie haben versucht, OptiVec durch manuelles Entpacken der erhaltenen .ZIP-Dateien zu installieren, ohne INSTALL.EXE zu benutzen. Dies ist nicht möglich, da INSTALL.EXE die Uhr für die Testzeit startet. Unter Windows 2000 / XP müssen Sie statt des hier nicht lauffähigen INSTALL.EXE die Initialisierungs-Routine InitOVBC.EXE (Borland C++-Version) bzw. InitOVVC.EXE (MSVC-Version) ausführen.

 

(0) Trial period for OptiVec/CMATH has expired!
Nur in der Shareware-Version: Die Testzeit ist abgelaufen. Wir hoffen, Sie haben sich von den Vorzügen der Programmierung mit OptiVec überzeugen können und würden uns sehr über Ihre Registrierung freuen!

 

(1) Not enough memory.
("Nicht genug Speicherplatz")
Sie versuchen, Speicher zuzuweisen, aber es ist nicht mehr genügend vorhanden. Dieser Fehler kommt vor allem im Zusammenhand mit "vergessenen Vektoren" in Schleifen vor, die alloziert, aber niemals freigegeben werden. Man versuche die folgenden Lösungen:
* Schnellstmögliche Freigabe aller nicht mehr gebrauchten Vektoren. Gehen Sie sicher, daß alle innerhalb eines Unterprogrammes erzeugten Vektoren wieder freigegeben werden, bevor das Unterprogramm verlassen wird.
* Arbeiten Sie noch mit 16-bit-Modellen und müssen große Datenmengen verarbeiten? Steigen Sie auf das Speichermodell FLAT für Win32 und Windows95/98/NT um, wodurch der volle RAM-Speicher (und gegebenenfalls außerdem noch virtueller Speicher) verfügbar wird.
* Lagern Sie Daten zwischendurch mittels VF_store auf Festplatte aus und lesen sie mit VF_recall wieder ein, wenn sie gebraucht werden. Diese Methode ist langsam und sollte nur im Notfall angewandt werden.

 

(2) Vector > 64 kB not possible (16-bit).
(2) Vector > 4 GB not possible (32-bit).
("Vektor > 4 GB bzw. 64 kB nicht möglich")
* Entweder versuchen Sie einen Vektor zu erzeugen, dessen Größe das Maximum von 4 GB (32-bit) bzw. 64 kB (16-bit-Speichermodelle außer HUGE) übersteigt.
* Oder Sie benutzen das Speichermodell HUGE und rufen eine der wenigen Funktionen auf, bei denen bestimmte Vektoren auf 64 kB limitiert sind (wie z.B. die Tabellen in den Interpolations-Funktionen). Sie müssen auf 64-bit umsteigen, wenn sich Ihr Problem nicht in kleinere Portionen zerlegen läßt.

 

(3) Vectors/matrices must not be identical.
("Vektoren/Matrizen dürfen nicht identisch sein")
Bei einigen Funktionen, wo mehr als ein Eingangs-Vektor (bzw. -Matrix) verwandt wird, um mehr als einen Ergebnis-Vektor zu berechnen, muß darauf geachtet werden, welcher Ergebnis-Vektor welchen Eingangs-Vektor überschreiben darf oder eben nicht. Vergleiche die Beschreibung der jeweiligen Funktion.

 

(4) Cannot use requested format (too many entries per line).
("Kann verlangtes Format nicht verwenden – zu viele Einträge pro Zeile.")
Dieser Fehler taucht bei den Ausgabe-Funktionen (VF_print usw.) auf. Der Parameter nperline wurde zu groß für den jeweiligen Datentyp und die zur Verfügung stehende Zeilenlänge angegeben. Die Funktion wählt automatisch die maximal mögliche Zahl der Einträge pro Zeile und setzt hiermit die Ausführung des Programmes fort.

 

(5) X-values of table must be distinct.
("X-Werte der Tabelle müssen unterschiedlich sein")
Die Interpolations-Routinen benötigen Tabellen, die gemäß ihren X-Werten geordnet sind. Jeder X-Wert darf nur einmal vorkommen, da unmöglich zu ein- und demselben X-Wert verschiedene Y-Werte gehören können.

 

(6) Not possible with fewer than n elements.
("Nicht möglich mit weniger als n Elementen")
Einige Funktionen verlangen das Vorhandensein einer minimalen Anzahl von n Vektor-Elementen.

 

(7) Not possible with more than n elements.
("Nicht möglich mit mehr als n Elementen")
Einige Funktionen begrenzen die Verarbeitung auf eine bestimmte Anzahl von n Vektor-Elementen (z.B. VF_polyinterpol, wo bis zu 10 Tabellen-Elemente für die Interpolation herangezogen werden können).

 

(8) Size must be an integer power of 2.
("Größe muß eine ganzzahlige Potenz von 2 sein")
Für alle Funktionen, die – explizit oder implizit – Fast-Fourier-Transform-Methoden anwenden, muß die Vektorgröße eine ganzzahlige Potenz von 2 sein. Man vergrößere oder verkleinere den/die Vektoren, um diese Bedingung zu erfüllen.

 

(9) Invalid parameter(s).
("Ungültige(r) Parameter")
In einigen Funktionen ist der zulässige Bereich eines oder mehrerer Eingabe-Parameter beschränkt. In anderen wiederum sind bestimmte Kombinationen von Eingabe-Parametern nicht erlaubt. So können Sie beispielsweise keine 9-Punkt-Interpolation mit nur 5 Datenpunkten durchführen.

 

(10) Cannot scale symbols by more than a factor of 50.
("Kann Symbole nicht mehr als fünfzigfach vergrößern." Nur Windows)
Die in den Plot-Funktionen von VectorLib verwendeten Symbole können nicht um mehr als einen Faktor 50 vergrößert werden (was allerdings bereits bedeutet, den ganzen Bildschirm mit einem einzigen Symbol zu füllen). Die Ausführung des Programmes wird nach dieser Meldung mit dem – immer noch ziemlich unsinnigen – Wert von 30 fortgesetzt.

 

(11) Cannot use line thicker than 500 pixels.
("Kann keine Linienstärke von mehr als 500 Pixels verwenden." Nur Windows)
Die Linienstärke in den Plot-Funktionen von VectorLib kann nicht diecker als 500 Pixels sein (was ohnehin ein ziemlich unsinniger Wert ist). Die Ausführung des Programmes wird nach dieser Meldung mit dem Wert von 500 fortgesetzt.

 

(12) Cannot free non-existent vector.
("Kann nicht-existierenden Vektor nicht freigeben.")
Sie haben V_free oder V_nfree für einen Vektor aufgerufen, dem gar kein Speicher zugeordnet ist. Die Ausführung des Programmes wird nach dieser Meldung fortgesetzt, ohne daß irgendetwas freigegeben wird.

 

(21) Invalid dimension(s).
("Ungültige Dimension(en).")
Auf die eine oder andere Weise erfüllen die Dimensionen von Ein- und Ausgabematrizen nicht die in der jeweiligen Funktionsbeschreibung genannten Bedingungen.

 

(22) Matrix is singular.
("Matrix ist singulär.")
In einer Funktion, die reguläre Eingabematrizen verlangt, wurde eine singuläre Matrix angetroffen. Sie sollten eine alternative Funktion verwenden, die für die Behandlung auch (nahezu) singulärer Matrizen ausgelegt ist.

 

(23) No convergence achieved.
("Keine Konvergenz erzielt.")
Einige iterative Matrix-Methoden können in sehr seltenen Fällen scheitern, indem auch nach zahlreichen Iterations-Durchläufen keine Konvergenz erreicht wurde.

 

(24) Only the first n elements of each row can be printed.
("Kann nur die ersten n Elemente jeder Zeile ausgeben.")
Dieser Fehler taucht bei den Matrix-Ausgabefunktionen (MF_print usw.) auf, wenn die Zahl der Spalten größer ist als auf den Bildschirm paßt. Die Funktion wählt automatisch die maximal mögliche Spaltenzahl und schneidet die Zeilen am Bildschirmrand ab.

Zurück zum VectorLib-Inhaltsverzeichnis     OptiVec Home


6. Wenn etwas schiefgeht

Wenn Sie Probleme mit OptiVec haben, sollten Sie zuerst prüfen, ob die Installation korrekt durchgeführt wurde (s. Kap. 1.4). Weiterhin sollte man sehr genau darauf achten, die folgenden Bedingungen einzuhalten, deren Nichtbeachtung unweigerlich Schwierigkeiten nach sich zieht.
  • Sie müssen die Wahl von Prozessor, Umgebung und OptiVec-Bibliothek in Übereinstimmung bringen. Mit der Bibliothek VCL3.LIB beispielsweise werden Sie unter Windows oder auf einem 286er Rechner nicht viel Freude haben. Auch mit dem "falschen" Compiler können OptiVec-Bibliotheken nicht laufen.
  • Vektoren der Größe 0 sind verboten. Alle Funktionen gehen stillschweigend davon aus, daß mindestens ein Element vorhanden ist und verschwenden Ihre Computer-Zeit nicht damit, dies zu testen.
  • Es reicht nicht aus, Vektoren nur zu deklarieren; ihnen muß auch Speicher zugewiesen werden. (siehe VF_vector). Wenn Sie die entsprechende Warnung nicht gerade ausgeschaltet haben, wird auch der Compiler Sie darauf hinweisen ("possible use of xxx before definition").
  • Konstante Parameter sollten eine Größe von 1.E32 für float / Single, 1.E150 für double und von 1.E2000 für extended nicht überschreiten. (Das müßte eigentlich reichen!)

Obwohl OptiVec gründlich getestet worden ist, besteht natürlich immer die Möglichkeit, daß ein Problem unserer Aufmerksamkeit entgangen ist. Sollten Sie das Gefühl haben, auf ein solches Problem zu stoßen, so versuchen Sie doch bitte, die zu seinem Auftauchen führenden Bedingungen so genau wie möglich zu spezifizieren, und lassen Sie es uns unter support@optivec.de wissen!

Zurück zum VectorLib-Inhaltsverzeichnis     OptiVec Home

7. Die Include-Dateien und Units von OptiVec

Alle C/C++-Include-Dateien von OptiVec haben dieselben Namen wie die entsprechenden Pascal/Delphi-Units. Natürlich ist die Namenserweiterung unterschiedlich: ".H" für die C/C++-Include-Dateien, ".DCU" für Delphi-Units und ".TPU" oder "TPP" für Pascal-Units. Unten werden nur die Namen ohne Erweiterung aufgeführt.

Nur C/C++: Man deklariere den Gebrauch von OptiVec-Funktionen mit #include-Anweisungen. Falls Sie MFC (Microsoft Foundation Classes) oder Borlands OWL (ObjectWindows Library) verwenden, müssen die MFC- oder OWL-Include-Dateien vor(!) denen von OptiVec eingeschlossen werden.

Nur Pascal/Delphi: Man deklariere den Gebrauch von OptiVec-Funktionen mit der uses-Anweisung.
 

Include-Datei (Suffix .H) oder UnitInhalt
VecLibgrundlegenden Definitionen der Datentypen und die Prototypen der allen Datentypen gemeinsamen Funktionen (das sind diejenigen mit dem Präfix V_) mit Ausnahme der Graphik-Routinen
VFstd, VDstd, VEstd"Standard-Operationen" für Fließkomma-Zahlen: Erzeugung und Initialisierung von Vektoren, Index-orientierte Manipulationen, Datentyp-Umwandlungen, I/O-Operationen, Statistik, Analysis, geometrische Vektor-Arithmetik und alle auf der Fourier-Transformation basierenden Funktionen.
VCFstd, VCDstd, VCEstd,
VPFstd, VPDstd, VPEstd
Standard-Operationen für cartesisch- und polar-komplexe Vektoren
VIstd, VBIstd, VSIstd, VLIstd, VQIstdStandard-Operationen für Ganzzahl-Vektoren mit Vorzeichen
VUstd, VUBstd, VUSstd, VULstd, VUIstdStandard-Operationen für vorzeichenlose Ganzzahl-Vektoren (VUIstd nur für C/C++)
VFmath, VDmath, VEmathAlgebraische, arithmetische und mathematische Funktionen für Fließkomma-Vektoren
VCFmath, VCDmath, VCEmath,
VPFmath, VPDmath, VPEmath
Arithmetische und mathematische Funktionen für komplexe Vektoren
VImath, VBImath, VSImath, VLImath, VQImathArithmetische und mathematische Funktionen für vorzeichenbehaftete Ganzzahl-Vektoren
VUmath, VUBmath, VUSmath, VULmath, VUImathArithmetische und mathematische Funktionen für vorzeichenlose Ganzzahl-Vektoren (VUImath nur für C/C++)
VgraphGraphik-Funktionen für alle Datentypen
VFNLFIT, VDNLFIT, VENLFITNicht-lineare Datenanpassungs-Funktionen (nur Pascal/Delphi; in C/C++ befinden sie sich in M?std)
VFMNLFIT, VDMNLFIT, VEMNLFITNicht-lineare Datenanpassungs-Funktionen für Mehrfach-Datensätze (nur Pascal/Delphi; in C/C++ befinden sie sich in M?std)
MFstd, MDstd, MEstdMatrix-Operationen für reelle Matrizen
MCFstd, MCDstd, MCEstdMatrix-Operationen für cartesisch-komplexe Matrizen
Mgraphgraphische Darstellung von Matrizen aller Datentypen
MFNLFIT, MDNLFIT, MENLFITNicht-lineare Datenanpassungs-Funktionen für Datensätze Z = f(X, Y)  (nur Pascal/Delphi; in C/C++ befinden sie sich in M?std)
MFMNLFIT, MDMNLFIT, MEMNLFITNicht-lineare Datenanpassungs-Funktionen für Mehrfach-Datensätze Z = f(X, Y)  (nur Pascal/Delphi; in C/C++ befinden sie sich in M?std)
NEWCPLXkomplexe Klassenbibliothek CMATH; nur C++
CMATHkomplexe Bibliothek CMATH für Pascal/Delphi und C
CFMATH, CDMATH, CEMATHnur C/C++: typenspezifische Teile von CMATH
XMATHEinige skalare mathematische Funktionen, die intern von anderen OptiVec-Funktionen benötigt werden; sie stehen allgemein für Anwendungen zur Verfügung. C/C++: die Sinus-, Cosecans- und Tangens-Tabellen für VF_sinrpi2 etc. befinden sich ebenfalls hier.
FSINTAB2, DSINTAB2, ESINTAB3,
FSINTAB3, DSINTAB3, ESINTAB3
Sinus-Tabellen (nur Pascal/Delphi; für C/C++ befinden sie sich in XMATH)
FCSCTAB2, DCSCTAB2, ECSCTAB3,
FCSCTAB3, DCSCTAB3, ECSCTAB3
Cosecans-Tabellen (nur Pascal/Delphi; für C/C++ befinden sie sich in XMATH)
FTANTAB2, DTANTAB2, ETANTAB3,
FTANTAB3, DTANTAB3, ETANTAB3
Tangens-Tabellen (nur Pascal/Delphi; für C/C++ befinden sie sich in XMATH)
VecObjgrundlegende Definitionen für VecObj, das Objekt-orientierte Interface für C++
fVecObj, dVecObj, eVecObjMember-Funktionen von VecObj für reelle Vektor-Objekte (nur C++)
cfVecObj, cdVecObj, ceVecObj
pfVecObj, pdVecObj, peVecObj
Member-Funktionen von VecObj für komplexe Vektor-Objekte (nur C++)
iVecObj, biVecObj, siVecObj, liVecObj, qiVecObjMember-Funktionen von VecObj für vorzeichenbehaftete Ganzzahl-Vektor-Objekte (nur C++)
uVecObj, ubVecObj, usVecObj, ulVecObj, uiVecObjMember-Funktionen von VecObj für vorzeichenlose Ganzzahl-Vektor-Objekte (nur C++)
OptiVecschließt das gesamte OptiVec-Paket ein (nur C++)
VecAllschließt alle VectorLib- und CMATH-Funktionen ein (nur C oder C++)
MatAllschließt alle MatrixLib-Funktionen ein (nur C oder C++)
 

Zurück zum VectorLib-Inhaltsverzeichnis     OptiVec Home

Copyright © 1998-2016 OptiCode – Dr. Martin Sander Software Development

Letzte Aktualisierung: 18. Oktober 2016