Ausdrücke (Object Pascal)

Aus Appmethod Topics
Wechseln zu: Navigation, Suche

Nach oben zu Grundlegende syntaktische Elemente - Index

In diesem Thema werden die Syntaxregeln für Object Pascal-Ausdrücke beschrieben.

Folgende Bereiche werden behandelt:

  • Gültige Object Pascal-Ausdrücke
  • Operatoren
  • Funktionsaufrufe
  • Mengenkonstruktoren
  • Indizes
  • Typumwandlungen

Ausdrücke

Ein Ausdruck ist eine Konstruktion, die einen Wert zurückliefert. Die folgende Tabelle enthält Beispiele für Object Pascal-Ausdrücke:

X

Variable

@X

Adresse der Variable X

15

Integer-Konstante

InterestRate

Variable

Calc(X, Y)

Funktionsaufruf

X * Y

Produkt von X und Y

Z / (1 - Z)

Quotient von Z und (1 - Z)

X = 1.5

Boolescher Ausdruck

C in Range1

Boolescher Ausdruck

not Done

Negation eines booleschen Ausdrucks

['a', 'b', 'c']

Menge

Char(48)

Wert einer Typumwandlung


Die einfachsten Ausdrücke sind Variablen und Konstanten (siehe Datentypen, Variablen und Konstanten). Komplexere Ausdrücke werden mithilfe von Operatoren, Funktionsaufrufen, Mengenkonstruktoren, Indizes und Typumwandlungen aus einfachen Ausdrücken gebildet.

Operatoren

Operatoren verhalten sich wie vordefinierte Funktionen, die Bestandteil der Sprache Object Pascal sind. So setzt sich beispielsweise der Ausdruck (X + Y) aus den Variablen X und Y (den so genannten Operanden) und dem Operator + zusammen. Wenn X und Y den Typ Integer oder Real haben, liefert der Ausdruck (X + Y) die Summe der beiden Werte. Operatoren sind @, not, ^, *, /, div, mod, and, shl, shr, as, +, -, or, xor, =, >, <, <>, <=, >=, in und is.

Die Operatoren @, not und ^ sind unäre Operatoren und haben nur einen Operanden. Alle anderen Operatoren sind binär und haben zwei Operanden. Eine Ausnahme bilden die Operatoren + und -, die entweder unär oder binär sein können. Ein unärer Operator steht immer vor seinem Operanden (z. B. -B). Eine Ausnahme von dieser Regel bildet der Operator ^, der auf seinen Operanden folgt (z. B. P^). Binäre Operatoren stehen immer zwischen ihren Operanden (z. B. A = 7).

Das Verhalten einiger Operatoren hängt von dem Datentyp ab, der an sie übergeben wird. Beispielsweise führt der Operator not eine bitweise Negation eines Integer-Operanden und eine logische Negation eines booleschen Operanden aus. Solche Operatoren werden deshalb auch mehreren Kategorien zugeordnet.

Mit Ausnahme von ^, is und in können alle Operatoren Operanden vom Typ Variant akzeptieren. Weitere Informationen finden Sie unter Variante Typen.

Bei den Erläuterungen in den folgenden Abschnitten wird davon ausgegangen, dass Sie mit den Datentypen von Object Pascal vertraut sind. Weitere Informationen finden Sie unter Datentypen, Variablen und Konstanten.

Informationen zur Rangfolge der Operatoren in komplexen Ausdrücken finden Sie unter "Rangfolge von Operatoren" weiter unten.

Arithmetische Operatoren

Zu den arithmetischen Operatoren für Real- oder Integer-Operanden gehören die Operatoren +, -, *, /, div und mod.

Binäre arithmetische Operatoren:

Operator Operation Operandtyp Ergebnistyp Beispiel

+

Addition

Integer, Real

Integer, Real

X + Y

-

Subtraktion

Integer, Real

Integer, Real

Result -1

*

Multiplikation

Integer, Real

Integer, Real

P * InterestRate

/

Gleitkommadivision

Integer, Real

Real

X / 2

div

Ganzzahlige Division

Integer

Integer

Total div UnitSize

mod

Rest

Integer

Integer

Y mod 6


Unäre arithmetische Operatoren:

Operator Operation Operandtyp Ergebnistyp Beispiel

+

Positives Vorzeichen

Integer, Real

Integer, Real

+7

-

Negatives Vorzeichen

Integer, Real

Integer, Real

-X


Für arithmetische Operatoren gelten die folgenden Regeln:

  • Der Wert von x / y hat den Typ Extended, ungeachtet der Typen von x und y. Bei allen anderen Operatoren hat das Ergebnis den Typ Extended, wenn mindestens ein Operand den Typ Real hat. Ist das nicht der Fall, hat das Ergebnis den Typ Int64, wenn mindestens ein Operand den Typ Int64 hat, ansonsten hat das Ergebnis den Typ Integer. Wenn der Typ eines Operanden ein Unterbereich eines Integer-Typs ist, wird er wie ein Operand vom Typ Integer behandelt.
  • Der Wert von x div y entspricht dem Wert von x / y, abgerundet in Richtung null bis zum nächsten Integer-Wert.
  • Der Operator mod liefert den Rest, der sich bei der Division seiner Operanden ergibt. Das bedeutet:
    x mod y = x - (x div y) * y.
  • Wenn y in einem Ausdruck der Form x / y, x div y oder x mod y den Wert null hat, tritt ein Laufzeitfehler auf.

Boolesche Operatoren

Die Operanden der booleschen Operatoren not, and, or und xor können einen beliebigen booleschen Typ haben. Die Operatoren liefern einen Wert vom Typ Boolean zurück.

Boolesche Operatoren:

Operator Operation Operandtyp Ergebnistyp Beispiel

not

Negation

Boolean

Boolean

not (C in MySet)

and

Konjunktion

Boolean

Boolean

Done and (Total >0)

or

Disjunktion

Boolean

Boolean

A or B

xor

Exklusive Disjunktion

Boolean

Boolean

A xor B

Diese Operatoren folgen den Standardregeln der booleschen Logik. Beispielsweise liefert ein Ausdruck der Form x and y nur dann den Wert True, wenn x und y den Wert True haben.

Vollständige Auswertung und Kurzschlussverfahren im Vergleich

Der Compiler unterstützt zwei Auswertungsmodi für die Operatoren and und or: die vollständige Auswertung und das Kurzschlussverfahren. Bei der vollständigen Auswertung werden alle Operanden eines and- oder or-Ausdrucks auch dann ausgewertet, wenn das Resultat des gesamten Ausdrucks bereits feststeht. Das Kurzschlussverfahren geht streng von links nach rechts vor und wird beendet, sobald das Ergebnis des gesamten Ausdrucks feststeht. Wenn beispielsweise der Ausdruck A and B im Kurzschlussverfahren ausgewertet wird und A den Wert False hat, wertet der Compiler B nicht mehr aus, da bereits feststeht, dass nach der Auswertung von A auch der gesamte Ausdruck den Wert False hat.

Das Kurzschlussverfahren ist normalerweise vorzuziehen, da es schneller ausgeführt wird und (in den meisten Fällen) einen geringeren Quelltextumfang erfordert. Die vollständige Auswertung ist von Nutzen, wenn ein Operand eine Funktion mit Nebeneffekten ist, die Änderungen in der Ausführung des Programms bewirken.

Das Kurzschlussverfahren ermöglicht auch Konstruktionen, die sonst zu unzulässigen Laufzeitoperationen führen würden. Die folgende Anweisung iteriert bis zum ersten Komma durch den String S:

while (I <= Length(S)) and (S[I] <> ',') do
begin
 ...
 Inc(I);
end;

Wenn S kein Komma enthält, wird I bei der letzten Iteration auf einen Wert erhöht, der größer ist als S. Beim nachfolgenden Test der while-Bedingung wird bei einer vollständigen Auswertung versucht, S[I] zu lesen, was zu einem Laufzeitfehler führen kann. Beim Kurzschlussverfahren wird dagegen der zweite Teil der while-Bedingung (S[I] <> ',') nicht mehr ausgewertet, nachdem der erste Teil False ergibt.

Zur Steuerung des Auswertungsmodus dient die Compiler-Direktive $B. Voreingestellt ist der Status {$B}, mit dem Kurzschlussverfahren aktiviert wird. Um die vollständige Auswertung lokal zu aktivieren, fügen Sie die Direktive {$B+} in den Quelltext ein. Sie können auch auf Projektebene in diesen Status wechseln, indem Sie im Dialogfeld Projektoptionen die Option Boolesche Ausdrücke vollständig aktivieren (alle Quell-Units müssen erneut compiliert werden).

Hinweis: Wenn einer der Operanden den Typ Variant hat, führt der Compiler immer eine vollständige Auswertung durch (auch im Status {$B}).

Logische (bitweise) Operatoren

Die folgenden logischen Operatoren verarbeiten Integer-Operanden bitweise. Wenn z. B. der in X (binär) gespeicherte Wert 001101 und der in Y gespeicherte Wert 100001 lautet, weist die Operation

Z := X or Y;

Z den Wert 101101 zu.

Logische (bitweise) Operatoren:

Operator Operation Operandtyp Ergebnistyp Beispiel

not

Bitweise Negation

Integer

Integer

not X

and

Bitweises UND

Integer

Integer

X and Y

or

Bitweises ODER

Integer

Integer

X or Y

xor

Bitweises exklusives ODER

Integer

Integer

X xor Y

shl

Bitverschiebung nach links

Integer

Integer

X shl 2

shr

Bitverschiebung nach rechts

Integer

Integer

Y shr I

Für bitweise Operatoren gelten die folgenden Regeln:

  • Das Ergebnis einer not-Operation hat denselben Typ wie der Operand.
  • Wenn beide Operanden einer and-, or- oder xor-Operation Integer-Typen sind, hat das Ergebnis den vordefinierten Integer-Typ mit dem kleinsten Bereich, im dem alle für beide Typen möglichen Werte enthalten sind.
  • Die Operationen x shl y und x shr y verschieben den Wert von x um y Bits nach links oder rechts (falls es sich bei x um einen vorzeichenlosen Integer handelt). Dies entspricht der Multiplikation oder Division von x durch 2^y. Das Ergebnis hat denselben Typ wie x. Wenn beispielsweise in N der Wert 01101 (dezimal 13) gespeichert ist, gibt N shl 1 den Wert 11010 (dezimal 26) zurück. Beachten Sie, dass der Wert von y als Restwert der Größe von Typ x interpretiert wird. Wenn z. B. x ein Integer ist, wird x shl 40 als x shl 8 interpretiert, da ein Integer 32 Bit hat, und 40 minus 32 den Wert 8 ergibt.

Beispiel

Wenn x ein negativer Integer-Wert ist, werden die Operationen shl und shr folgendermaßen ausgedrückt:

 var
   x: integer;
   y: string;
 
 ...
 begin
   x := -20;
   x := x shr 1;
   //As the number is shifted to the right by 1 bit, the sign bit's value replaced is with 0 (all negative numbers have the sign bit set to 1).
   y := IntToHex(x, 8);
   writeln(y);
   //Therefore, x is positive.
   //Decimal value: 2147483638
   //Hexadecimal value: 7FFFFFF6
   //Binary value: 0111 1111 1111 1111 1111 1111 1111 0110
 end.

String-Operatoren

Die relationalen Operatoren =, <>, <, >, <= und >= übernehmen alle String-Operanden (siehe "Relationale Operatoren" weiter unten in diesem Abschnitt). Der Operator + verkettet zwei Strings.

String-Operatoren:

Operator Operation Operandtyp Ergebnistyp Beispiel

+

Verkettung

String, gepackter String, Char

String

S + '.'


Für die Verkettung von Strings gelten folgende Regeln:

  • Die Operanden für + können Strings, gepackte Strings (gepackte Arrays vom Typ Char) oder Zeichen sein. Wenn jedoch ein Operand den Typ WideChar hat, muss der andere Operand ein langer String (UnicodeString, AnsiString oder WideString) sein.
  • Das Ergebnis einer +-Operation ist mit allen String-Typen kompatibel. Wenn aber beide Operanden kurze Strings oder Zeichen sind und ihre gemeinsame Länge größer als 255 ist, wird das Ergebnis nach dem 255. Zeichen abgeschnitten.

Zeiger-Operatoren

Zeichenzeiger-Operatoren:

Operator Operation Operandtyp Ergebnistyp Beispiel

+

Zeigeraddition

Zeichenzeiger, Integer

Zeichenzeiger

P + I

-

Zeigersubtraktion

Zeichenzeiger, Integer

Zeichenzeiger, Integer

P - Q

^

Zeiger-Dereferenzierung

Zeiger

Basistyp von Zeiger

P^

=

Gleich

Zeiger

Boolean

P = Q

<>

Ungleich

Zeiger

Boolean

P <> Q


Der Operator ^ dereferenziert einen Zeiger. Sein Operand kann ein Zeiger auf einen beliebigen Typ mit Ausnahme des generischen Typs Pointer sein, der vor der Dereferenzierung umgewandelt werden muss.

P = Q ist nur dann True, wenn P und Q auf dieselbe Adresse zeigen. Andernfalls ergibt P <> QTrue.

Mit den Operatoren + und - kann der Offset eines Zeichenzeigers erhöht oder verringert werden. Mit dem Operator - können Sie außerdem den Unterschied zwischen den Offsets zweier Zeichenzeiger berechnen. Es gelten die folgenden Regeln:

  • Wenn I ein Integer und P ein Zeichenzeiger ist, addiert P + I den Wert I zu der von P angegebenen Adresse. Es wird also ein Zeiger auf die Adresse zurückgegeben, die I Zeichen hinter P liegt. (Der Ausdruck I + P entspricht P + I.) P - I subtrahiert I von der Adresse, die von P angegeben wird. Das Ergebnis ist ein Zeiger auf die Adresse, die I Zeichen vor P liegt. Dies gilt für PAnsiChar-Zeiger. Für PWideChar-Zeiger fügt P + II * SizeOf(WideChar) zu P hinzu.
  • Wenn P und Q Zeichenzeiger sind, berechnet P - Q die Differenz zwischen der von P angegebenen (höheren) und der von Q angegebenen (niedrigeren) Adresse. Es wird also ein Integer-Wert für die Anzahl der Zeichen zwischen P und Q zurückgegeben.
Das Ergebnis von P + Q ist nicht definiert.

Mengenoperatoren

Die folgenden Operatoren haben eine Menge als Operanden.

Mengenoperatoren:

Operator Operation Operandtyp Ergebnistyp Beispiel

+

Union

Menge

Menge

Set1 + Set2

-

Differenz

Menge

Menge

S - T

*

Schnittmenge

Menge

Menge

S * T

<=

Untermenge

Menge

Boolean

Q <= MySet

>=

Obermenge

Menge

Boolean

S1 >= S2

=

Gleich

Menge

Boolean

S2 = MySet

<>

Ungleich

Menge

Boolean

MySet <> S1

in

Element einer Menge

Ordinalwert, Menge

Boolean

A in Set1


Für +, - und * gelten die folgenden Regeln:

  • Der Ordinalwert O ist nur in X + Y enthalten, wenn O in X oder Y (oder beiden) enthalten ist. O ist nur in X - Y enthalten, wenn O in X, aber nicht in Y enthalten ist. O ist nur in X * Y enthalten, wenn O sowohl in X als auch in Y enthalten ist.
  • Das Ergebnis einer Operation mit +, - oder * hat den Typ set of A..B, wobei A der kleinste und B der größte Ordinalwert in der Ergebnismenge ist.

Für <=, >=, =, <> und in gelten die folgenden Regeln:

  • X <= Y ist True, wenn jedes Element von X ein Element von Y ist. Z >= W ist gleichbedeutend mit W <= Z. U = V ist nur dann True, wenn U und V genau dieselben Elemente enthalten. Andernfalls gilt U <> V ist True.
  • Für einen Ordinalwert O und eine Menge S ist O in S nur dann True, wenn O ein Element von S ist.

Relationale Operatoren

Relationale Operatoren dienen dem Vergleich zweier Operanden. Die Operatoren =, <>, <= und >= können auch für Mengen angewendet werden.

Relationale Operatoren:

Operator Operation Operandtyp Ergebnistyp Beispiel

=

Gleich

Einfacher Typ, Klassen-, Klassenreferenz-, Interface-, String- und gepackter String-Typ

Boolean

I = Max

<>

Ungleich

Einfacher Typ, Klassen-, Klassenreferenz-, Interface-, String- und gepackter String-Typ

Boolean

X <> Y

<

Kleiner als

Einfacher Typ, String-, gepackter String und PChar-Typ

Boolean

X < Y

>

Größer als

Einfacher Typ, String-, gepackter String und PChar-Typ

Boolean

Len > 0

<=

Kleiner oder gleich

Einfacher Typ, String-, gepackter String und PChar-Typ

Boolean

Cnt <= I

>=

Größer oder gleich

Einfacher Typ, String-, gepackter String und PChar-Typ

Boolean

I >= 1


Bei den meisten einfachen Typen ist der Vergleich unkompliziert. I = J ist beispielsweise nur dann True, wenn I und J denselben Wert haben. Andernfalls ist I <> JTrue. Für relationale Operatoren gelten die folgenden Regeln:

  • Operanden müssen kompatible Typen haben, mit folgender Ausnahme: Reelle und Integer-Typen können miteinander verglichen werden.
  • Strings werden gemäß den ordinalen Werten verglichen, die die Zeichen ausmachen, aus denen wiederum der String besteht. Zeichen-Typen werden als Strings der Länge 1 behandelt.
  • Zwei gepackte Strings müssen beim Vergleich dieselbe Anzahl von Komponenten aufweisen. Wird ein gepackter String mit n Komponenten mit einem String verglichen, wird der gepackte String als String der Länge n behandelt.
  • Die Operatoren <, >, <= und >= werden nur dann für den Vergleich von PAnsiChar-Operanden (sowie PWideChar) verwendet, wenn die beiden Zeiger auf Elemente in demselben Zeichen-Array zeigen.
  • Die Operatoren = und <> können Operanden von Klassen- und Klassenreferenztypen haben. Mit Operanden eines Klassentyps werden = und <> entsprechend den Regeln für Zeiger ausgewertet: C = D ist nur dann True, wenn C und D auf dasselbe Instanzobjekt zeigen. Ansonsten ist C <> DTrue. Mit Operanden eines Klassenreferenztyps ist C = D nur dann True, wenn C und D dieselbe Klasse bezeichnen. Andernfalls ist C <> DTrue. Damit werden keine Daten verglichen, die in Klassen gespeichert sind. Weitere Informationen zu Klassen finden Sie unter Klassen und Objekte.

Klassen- und Interface-Operatoren

Die Operatoren as und is übernehmen Klassen und Instanzobjekte als Operanden; as kann auch für Interfaces angewendet werden. Weitere Informationen finden Sie unter Klassen und Objekte, Objekt-Interfaces und Interface-Referenzen.

Die relationalen Operatoren = und <> können auch für Klassen angewendet werden.

Der Operator @

Der Operator @ liefert die Adresse einer Variablen, Funktion, Prozedur oder Methode, erzeugt also einen Zeiger auf seinen Operanden. Weitere Informationen über Zeiger finden Sie im Abschnitt "Zeiger und Zeigertypen" unter Datentypen, Variablen und Konstanten. Für den Operator @ gelten folgende Regeln:

  • Ist X eine Variable, gibt @X die Adresse von X zurück. (Wenn X eine prozedurale Variable ist, gelten besondere Regeln; siehe "Prozedurale Typen in Anweisungen und Ausdrücken" unter Datentypen, Variablen und Konstanten.) @X ist hat den Typ Pointer, wenn die Standard-Compiler-Direktive {$T} aktiviert ist. Im Status {$T+} hat @X den Typ ^T, wobei T denselben Typ wie X hat (dieser Unterschied ist für die Zuweisungskompatibilität wichtig; siehe "Zuweisungskompatibilität").
  • Wenn F eine Routine (eine Funktion oder Prozedur) ist, liefert @F den Eintrittspunkt von F. @F hat immer den Typ Pointer.
  • Wenn @ auf eine in einer Klasse definierte Methode angewendet wird, muss der Methodenbezeichner mit dem Klassennamen qualifiziert werden. Zum Beispiel:
@TMyClass.DoSomething
Diese Anweisung zeigt auf die Methode DoSomething von TMyClass. Weitere Informationen zu Klassen und Methoden finden Sie unter Klassen und Objekte.

Hinweis: Bei Verwendung des Operators @ ist es nicht möglich, die Adresse einer Interface-Methode anzugeben, da die Adresse zur Compilierzeit nicht bekannt ist und zur Laufzeit nicht extrahiert werden kann.

Rangfolge von Operatoren

In komplexen Ausdrücken wird die Reihenfolge, in der Operationen ausgeführt werden, durch die Rangfolge der Operatoren festgelegt.

Rangfolge von Operatoren

Operatoren Rangfolge

@
not

Erste (höchste) Wertigkeit

*
/
div
mod
and
shl
shr
as

Zweite Wertigkeit

+
-
or
xor

Dritte Wertigkeit

=
<>
<
>
<=
>=
in
is

Vierte (niedrigste) Wertigkeit


Ein Operator mit einer höheren Wertigkeit wird vor einem Operator mit einer niedrigeren Wertigkeit ausgewertet. Gleichrangige Operatoren werden von links nach rechts ausgewertet. Aus diesem Grund multipliziert der Ausdruck

X + Y * Z

zunächst Y mit Z und addiert dann X zum Ergebnis der Multiplikation. Die Operation * (Multiplikation) wird zuerst ausgeführt, weil dieser Operator höherwertiger ist als der Operator +. Dagegen wird beim Ausdruck:

X - Y + Z

zuerst Y von X subtrahiert und anschließend Z zum Ergebnis addiert. Die Operatoren - und + weisen dieselbe Wertigkeit auf. Aus diesem Grund wird die Operation auf der linken Seite zuerst ausgeführt.

Mithilfe von runden Klammern lassen sich die Rangfolgeregeln außer Kraft setzen. Ein Ausdruck in runden Klammern wird immer zuerst ausgewertet und danach wie ein einzelner Operand behandelt. Zum Beispiel:

(X + Y) * Z

Dieser Ausdruck multipliziert Z mit der Summe von X und Y.

Manchmal sind Klammern in Situationen erforderlich, die dies auf den ersten Blick nicht vermuten lassen. Betrachten Sie den folgenden Ausdruck:

X = Y or X = Z

Die beabsichtigte Interpretation lautet offensichtlich:

(X = Y) or (X = Z)

Wenn keine Klammern gesetzt werden, hält sich der Compiler an die Regeln für die Rangfolge der Operatoren und interpretiert den Ausdruck folgendermaßen:

(X = (Y or X)) = Z

Wenn Z kein boolescher Typ ist, führt dies zu einem Compilierungsfehler.

Runde Klammern erleichtern häufig das Schreiben und Lesen des Quelltextes, auch wenn sie streng genommen überflüssig sind. Das erste der obigen Beispiele könnte auch folgendermaßen formuliert werden:

X + (Y * Z)

Hier sind die Klammern (für den Compiler) unnötig, erleichtern aber dem Programmierer und dem Leser die Interpretation, weil die Rangfolge der Operatoren nicht berücksichtigt werden muss.

Funktionsaufrufe

Funktionsaufrufe sind Ausdrücke, da sie einen Wert zurückliefern. Wenn Sie beispielsweise eine Funktion mit dem Namen Calc definiert haben, die zwei Integer-Argumente übernimmt und einen Integer-Wert zurückgibt, stellt der Funktionsaufruf Calc(24,47) einen Integer-Ausdruck dar. Sind I und J Integer-Variablen, ist I + Calc(J,8) ebenfalls ein Integer-Ausdruck. Hier einige Beispiele für Funktionsaufrufe:

Sum(A, 63)
Maximum(147, J)
Sin(X + Y)
Eof(F)
Volume(Radius, Height)
GetValue
TSomeObject.SomeMethod(I,J);

Weitere Informationen zu Funktionen finden Sie unter Prozeduren und Funktionen.

Mengenkonstruktoren

Ein Mengenkonstruktor bezeichnet einen Wert eines Mengentyps. Zum Beispiel:

[5, 6, 7, 8]

Dieser Mengenkonstruktor bezeichnet eine Menge mit den Ziffern 5, 6, 7 und 8. Dieselbe Menge könnte auch mit dem Mengenkonstruktor

[ 5..8 ]

bezeichnet werden.

Die Syntax für einen Mengenkonstruktor lautet:

[ Element1, ..., Elementn ]

Hierbei kann Element ein Ausdruck sein, der einen Ordinalwert des Basistyps der Menge bezeichnet, oder ein Paar solcher Ausdrücke, die durch zwei Punkte (..) miteinander verbunden sind. Hat Element die Form x..y, bezeichnet es alle Ordinalwerte von x bis einschließlich y. Ist x jedoch größer als y, repräsentiert x..y keine Elemente, und [x..y] steht für eine leere Menge. Der Mengenkonstruktor [ ] bezeichnet die leere Menge, während [x] eine Menge repräsentiert, deren einziges Element der Wert x ist.

Hier einige Beispiele für Mengenkonstruktoren:


[red, green, MyColor]
[1, 5, 10..K mod 12, 23]
['A'..'Z', 'a'..'z', Chr(Digit + 48)]

Weitere Informationen zu Mengen finden Sie im Abschnitt Strukturierte Typen unter Datentypen, Variablen und Konstanten.

Indizes

Strings, Arrays, Array-Eigenschaften und Zeiger auf Strings oder Arrays können indiziert werden. Beispielsweise liefert der Ausdruck Dateiname[3] für die String-Variable Dateiname den dritten Buchstaben in dem durch Dateiname bezeichneten String. Dagegen gibt Dateiname[I + 1] das Zeichen zurück, das unmittelbar auf das mit I indizierte Zeichen folgt. Weitere Informationen zu Strings finden Sie unter Datentypen, Variablen und Konstanten. Informationen zu Arrays und Array-Eigenschaften finden Sie im Abschnitt Arrays unter Datentypen, Variablen und Konstanten und im Abschnitt Array-Eigenschaften auf der Seite Eigenschaften.

Typumwandlungen

In bestimmten Situationen ist es erforderlich, den Typ eines Ausdrucks zu ändern. Durch eine Typumwandlung kann einem Ausdruck vorübergehend ein anderer Typ zugeordnet werden. Beispielsweise konvertiert die Anweisung Integer('A') den Buchstaben A in einen Integer.

Die Syntax für eine Typumwandlung lautet:

typeIdentifier(expression)

Handelt es sich bei dem Ausdruck um eine Variable, spricht man von einer Variablenumwandlung, andernfalls von einer Wertumwandlung. Obwohl die Syntax einer Wertumwandlung mit derjenigen einer Variablenumwandlung identisch ist, gelten für die beiden Umwandlungsarten unterschiedliche Regeln.

Wertumwandlungen

Bei einer Wertumwandlung müssen sowohl der Typbezeichner als auch der umzuwandelnde Ausdruck entweder ein ordinaler Typ oder ein Zeigertyp sein. Hier einige Beispiele für Wertumwandlungen:


Integer('A')
Char(48)
Boolean(0)
Color(2)
Longint(@Buffer)

Der resultierende Wert ergibt sich aus der Umwandlung des Ausdrucks in Klammern. Dabei wird der ursprüngliche Wert möglicherweise abgeschnitten oder erweitert, wenn die Größe des neuen Typs sich vom Typ des Ausdrucks unterscheidet. Das Vorzeichen des Ausdrucks bleibt aber in jedem Fall erhalten.

Die Anweisung

I := Integer('A');

weist der Variablen I den Wert von Integer('A') zu (also 65).

Auf eine Wertumwandlung dürfen keine Qualifizierer folgen. Außerdem sind Wertumwandlungen nur auf der rechten Seite einer Zuweisung erlaubt.

Variablenumwandlungen

Variablen können in jeden beliebigen Typ umgewandelt werden. Dabei muss allerdings die Größe gleich bleiben, und Integer-Typen dürfen nicht mit Real-Typen vermischt werden (verwenden Sie zur Umwandlung numerischer Typen Standardfunktionen wie Int und Trunc). Hier einige Beispiele für Variablenumwandlungen:

Char(I)
Boolean(Count)
TSomeDefinedType(MyVariable)

Variablenumwandlungen sind auf beiden Seiten einer Zuweisung erlaubt. Beispiel:

var MyChar: char;
  ...
  Shortint(MyChar) := 122;

Bei dieser Umwandlung wird MyChar das Zeichen z (ASCII 122) zugewiesen.

Variablen können in prozedurale Typen umgewandelt werden. Ausgehend von den Deklarationen:

type Func = function(X: Integer): Integer;
var
  F: Func;
  P: Pointer;
  N: Integer;

sind z. B. folgende Zuweisungen möglich:

F := Func(P);     { Assign procedural value in P to F }
Func(P) := F;     { Assign procedural value in F to P }
@F := P;          { Assign pointer value in P to F }
P := @F;          { Assign pointer value in F to P }
N := F(N);        { Call function via F }
N := Func(P)(N);  { Call function via P }

Wie das folgende Beispiel zeigt, dürfen auf Variablenumwandlungen auch Qualifizierer folgen:

type
  TByteRec = record
     Lo, Hi: Byte;
  end;
  TWordRec = record
     Low, High: Word;
  end;
  PByte = ^Byte;

var
  B: Byte;
  W: Word;
  L: Longint;
  P: Pointer;

begin
  W := $1234;
  B := TByteRec(W).Lo;
  TByteRec(W).Hi := 0;
  L := $1234567;
  W := TWordRec(L).Low;
  B := TByteRec(TWordRec(L).Low).Hi;
  B := PByte(L)^;
end;

In diesem Beispiel wird mit TByteRec auf das niedrigst- und höchstwertige Byte eines Word zugegriffen. Über TWordRec erfolgt ein Zugriff auf das niedrigst- und höchstwertige Word eines Longint. Zu diesem Zweck könnten auch die vordefinierten Funktionen Lo und Hi verwendet werden. Die Variablenumwandlung bietet aber den Vorteil, dass sie auf der linken Seite einer Zuweisung stehen kann.

Weitere Informationen zur Typumwandlung von Zeigern finden Sie unter Zeiger und Zeigertypen (Object Pascal). Ausführliche Informationen zur Umwandlung von Klassen- und Interface-Typen finden Sie im Abschnitt "Der Operator as" unter Klassenreferenzen und Interface-Referenzen.

Siehe auch