home *** CD-ROM | disk | FTP | other *** search
Text File | 1992-10-15 | 43.8 KB | 1,059 lines |
- Die Programmiersprache Oberon (Revidierte Fassung) N.Wirth
-
- Make it as simple as possible, but not simpler.
- A. Einstein.
-
-
- 1. Einführung
-
- Oberon ist eine aus Modula-2 hervorgegangene universelle Programmiersprache,
- deren wesentliche Neuerung das Konzept der Typerweiterung darstellt, welches
- die Konstruktion neuer Datentypen auf der Basis bereits existierender
- und die Inbezugsetzung dieser Typen untereinander ermöglicht.Dieser Report ist
- nicht als Programmierkurs gedacht. Er ist bewußt knapp gehalten und soll als
- Referenz für Programmierer, Implementoren und Autoren von Handbüchern dienen.
-
- Fehlende Spezifikationen sind meistens beabsichtigt, da sich der betreffende
- Sachverhalt entweder aus den gegebenen Sprachregeln ableiten läßt, oder aber
- an solchen Stellen bewußt offen gelassen wird, an denen eine endgültige
- Festlegung unklug erscheint.
-
-
- 2. Syntax
-
- Eine Sprache besteht aus einer unendlichen Menge von Sätzen, welche sich gemäß
- ihrer Syntax herleiten lassen. Die Sätze der Sprache Oberon nennen wir
- Compilationseinheiten (Compilation Units); sie bestehen jeweils aus einer
- endlichen Folge vom Symbolen eines endlichen Vokabulars. Das Vokabular der
- Sprache Oberon besteht aus Namen (Identifiers), Zahlen (Numbers), Zeichenketten
- (Strings), Operatoren (Operators), Begrenzern (Delimiters) und Kommentaren.
-
- Die Elemente dieses Vokabulars werden lexikalische Symbole genannt und bestehen
- aus Zeichenfolgen. (Man beachte die Unterscheidung zwischen Symbolen und
- Zeichen.) Zur Beschreibung der Syntax wird ein erweiterter Backus Naur-
- Formalismus (EBNF) verwendet. Eckige Klammern [ und ] bedeuten hierin, daß die
- umschlossenen Konstrukte optional sind, und geschweifte Klammern { und }, daß
- der dazwischenstehende Satzteil (möglicherweise auch nullmalig) wiederholt
- werden darf. Syntaktische Einheiten (Nichtterminalsymbole) werden mit
- englischen Begriffen bezeichnet, welche intuitiv die Bedeutung ausdrücken.
- Symbole des Sprachvokabulars (Terminalsymbole) werden durch in
- Anführungszeichen eingeschlossene Zeichenketten bezeichnet, oder durch Worte in
- Großbuchstaben, sogenannte reservierte Worte. Die Syntaktischen Regeln
- (Produktionen) sind mit einem Dollarzeichen ($) am linken Zeilenrand markiert.
-
-
- 3. Vokabular und Darstellung
-
- Die Darstellung von Symbolen durch Zeichen ist mittels des ASCII-Zeichensatzes
- definiert. Symbole sind Namen, Zahlen, Zeichenketten, Operatoren, Begrenzer
- und Kommentare. Die folgenden lexikalischen Regeln sind einzuhalten:
- Leerzeichen und Zeilenbrüche dürfen nicht innerhalb von Symbolen auftreten
- (ausgenommen innerhalb von Kommentaren und Leerzeichen in Strings); sie werden
- ignoriert, es sei denn, sie wären absolut notwendig, um zwei
- aufeinanderfolgende Symbole zu trennen. Groß- und Kleinbuchstaben werden
- unterschieden.
-
- 1. Namen sind Folgen von Buchstaben und Ziffern. Das erste Zeichen muß ein
- Buchstabe sein.
-
- $ ident = letter {letter | digit}.
-
- Beispiele:
-
- x scan Oberon GetSymbol firstLetter
-
- 2. Zahlen sind vorzeichenlose Integerzahlen oder reelle Zahlen. Integerzahlen
- sind Folgen von Ziffern und können von einem Buchstaben gefolgt werden. Der
- Typ einer Zahl ist der Minimaltyp (siehe 6.1), zu dem die Zahl gehört. Folgt
- der Ziffernfolge kein Buchstabe, so handelt es sich um eine Zahl in dezimaler
- Darstellung. Der nachgestellte Buchstabe H bezeichnet die hexadezimale
- Darstellung. Eine reelle Zahl enthält immer einen Dezimalpunkt. Wahlweise
- kann auch ein dezimaler Skalierungsfaktor enthalten sein: Der Buchstabe E
- (oder D) wird gesprochen als "mal zehn hoch". Eine reelle Zahl ist vom Typ
- REAL, es sei denn, der Skalierungsfaktor wäre D; dann ist die Zahl vom Typ
- LONGREAL.
-
- $ number = integer | real.
- $ integer = digit {digit} | digit {hexDigit} "H" .
- $ real = digit {digit} "." {digit} [ScaleFactor].
- $ ScaleFactor = ("E" | "D") ["+" | "-"] digit {digit}.
- $ hexDigit = digit | "A" | "B" | "C" | "D" | "E" | "F".
- $ digit = "0" | "1" | "2" | "3" | "4" | "5" | "6" | "7" | "8" | "9".
-
- Beispiele:
-
- 1987
- 100H = 256
- 12.3
- 4.567E8 = 456700000
- 0.57712566D-6 = 0.000000577125663.
-
- Zeichenkonstanten werden entweder durch ein einzelnes Zeichen in
- Anführungszeichen, oder durch die Ordinalzahl des Zeichens in hexadezimaler
- Darstellung, gefolgt von dem Buchstaben X, gekennzeichnet.
-
- $ CharConstant = """ character """ | digit {hexDigit} "X".
-
- 4. Strings sind in Anführungszeichen (") eingeschlossene Zeichenfolgen. Ein
- String darf selbst keine Anführungszeichen enthalten. Die Anzahl der Zeichen
- eines Strings wird als seine Länge bezeichnet. Strings können Zeichenarrays
- zugewiesen werden und mit ihnen verglichen werden (siehe 9.1 und 8.2.4).
-
- $ string = """ {character} """ .
-
- Beispiele:
-
- "OBERON"
- "Don't worry!"
-
- 5. Operatoren und Begrenzer sind die nachfolgend aufgeführten speziellen
- Zeichen, Zeichenpaare und reservierten Worte. Reservierte Worte bestehen
- ausschließlich aus Großbuchstaben und können nicht in der Rolle von Namen
- verwendet werden.
-
- + := ARRAY IS TO
- - ^ BEGIN LOOP TYPE
- * = CASE MOD UNTIL
- / # CONST MODULE VAR
- ~ < DIV NIL WHILE
- & > DO OF WITH
- . <= ELSE OR
- , >= ELSIF POINTER
- ; .. END PROCEDURE
- | : EXIT RECORD
- ( ) IF REPEAT
- [ ] IMPORT RETURN
- { } IN THEN
-
- 6. Kommentare sind beliebige mit der Klammer (* beginnende und mit *) endende
- Zeichenfolgen, welche überall im Programm zwischen zwei Symbolen eingefügt
- werden dürfen. Kommentare haben keinen Einfluß auf die Bedeutung eines
- Programms.
-
-
- 4. Deklarationen und Sichtbarkeitsregeln
-
- Jeder Name in einem Programm muß mittels einer Deklaration eingeführt werden,
- es sei denn, es handle sich um einen vordefinierten Namen. Deklarationen
- dienen auch dazu, bestimmte bleibende Eigenschaften eines Objekts festzulegen,
- so z.B., ob es sich um eine Konstante, einen Typ, eine Variable oder eine
- Prozedur handelt.Der Name wird verwendet, um sich auf das damit verbundene
- Objekt zu beziehen. Dies ist nur innerhalb desjenigen Programmteils möglich,
- der im Gültigkeitsbereich der entsprechenden Deklaration liegt. Kein Name darf
- sich innerhalb eines einzelnen Gültigkeitsbereichs auf mehr als ein Objekt
- beziehen. Ein Gültigkeitsbereich erstreckt sich textuell vom Ort der Deklaration
- bis zum Ende des Blocks (Prozedur oder Modul), zu dem die Deklaration gehört;
- das Objekt ist somit lokal zu diesem Block. Folgende Zusätze gelten zu dieser
- Regel:
-
- 1. Wird ein Typ T definiert als POINTER TO T1 (siehe 6.4), dann darf der Name
- T1 im Text folgend der Deklaration von T vereinbart werden, aber nur im
- gleichen Gültigkeitsbereich.
-
- 2. Feldnamen einer Recorddeklaration (siehe 6.3) sind nur innerhalb von Feld-
- Bezeichnern gültig. Ein Name mit globalem Gültigkeitsbereich darf bei seiner
- Deklaration von einer Exportmarkierung (*) gefolgt sein, die anzeigt, daß er
- von seinem Modul exportiert wird. In diesem Falle darf der Name in anderen
- Modulen verwendet werden, sofern diese dessen Modul importieren. Dem Namen wird
- dann als Präfix der Name, der sein Modul bezeichnet, vorangestellt (siehe
- Kap. 11). Präfix und Name werden durch einen Punkt getrennt und gemeinsam
- qualifizierter Name genannt.
-
- $ qualident = [ident "."] ident.
- $ identdef = ident ["*"].
-
- Die folgenden Namen sind vordefiniert, ihre Bedeutung wird in den angegebenen
- Abschnitten erklärt:
-
- ABS (10.2) LEN (10.2)
- ASH (10.2) LONG (10.2)
- BOOLEAN (6.1) LONGINT (6.1)
- BYTE (6.1) LONGREAL (6.1)
- CAP (10.2) MAX (10.2)
- CHAR (6.1) MIN (10.2)
- CHR (10.2) NEW (6.4)
- DEC (10.2) ODD (10.2)
- ENTIER (10.2) ORD (10.2)
- EXCL (10.2) REAL (6.1)
- FALSE (6.1) SET (6.1)
- HALT (10.2) SHORT (10.2)
- INC (10.2) SHORTINT (6.1)
- INCL (10.2) SIZE (10.2)
- INTEGER (6.1) TRUE (6.1)
-
-
- 5. Konstantendeklarationen
-
- Eine Konstantendeklaration verbindet einen Namen mit einem konstanten Wert.
-
- $ ConstantDeclaration = identdef "=" ConstExpression.
- $ ConstExpression = expression.
-
- Ein konstanter Ausdruck kann während des Lesens des Quelltextes berechnet
- werden, ohne daß das Programm tatsächlich ausgeführt werden muß. Seine
- Operanden sind Konstanten (siehe Kap. 8). Beispiele für Konstanten-
- deklarationen sind
-
- N = 100
- limit = 2*N -1
- all = {0 .. WordSize-1}
-
-
- 6. Typdeklarationen
-
-
- Ein Datentyp bestimmt die Menge der Werte, welche Variablen dieses Typs
- annehmen können, und die anwendbaren Operatoren. Eine Typdeklaration verbindet
- einen Namen mit einem Typ; solche Assoziationen können mit Grundtypen (Basic
- Types), oder mit strukturierten Typen geschehen. Im letzteren Fall wird
- hierdurch auch die Struktur aller Variablen dieses Typs festgelegt und,
- implizit, auch die Operatoren, die auf Komponenten solcher Variablen anwendbar
- sind. Es gibt zwei Arten von strukturierten Datentypen, nämlich Arrays
- (Vektoren, Matrizen) und Records (Verbundtypen), die sich in der Art des
- Zugriffs auf die Komponenten unterscheiden.
-
- $ TypeDeclaration = identdef "=" type.
- $ type = qualident | ArrayType | RecordType | PointerType | ProcedureType.
-
- Beispiele:
-
- Table = ARRAY N OF REAL
-
- Tree = POINTER TO Node
-
- Node = RECORD key: INTEGER;
- left, right: Tree
- END
-
- CenterNode = RECORD (Node)
- name: ARRAY 32 OF CHAR;
- subnode: Tree
- END
-
- Function* = PROCEDURE (x: INTEGER): INTEGER
-
- 6.1. Grundtypen
-
- Die folgenden Grundtypen sind durch vordefinierte Namen gekennzeichnet. Die
- anwendbaren Operatoren werden in Kap. 8.2 beschrieben und die zugehörigen
- vordefinierten Funktionen in Kap. 10.2. Die Wertebereiche der Grundtypen sind
- wie folgt:
-
- 1. BOOLEAN die Wahrheitswerte TRUE und FALSE.
- 2. CHAR die Menge der ASCII-Werte (0X ... 0FFX).
- 3. SHORTINT die Integerzahlen von MIN(SHORTINT) bis MAX(SHORTINT).
- 4. INTEGER die Integerzahlen von MIN(INTEGER) bis MAX(INTEGER).
- 5. LONGINT die Integerzahlen von MIN(LONGINT) bis MAX(LONGINT).
- 6. REAL die reellen Zahlen von MIN(REAL) bis MAX(REAL).
- 7. LONGREAL die reellen Zahlen von MIN(LONGREAL) bis MAX(LONGREAL).
- 8. SET die Menge der Integerzahlen von 0 bis MAX(SET).
- 9. BYTE (siehe 9.1 und 10.1)
-
- Die Typen 3 bis 5 sind Integertypen und 6 und 7 sind reelle Typen. Zusammen
- bezeichnen wir sie als numerische Typen. Sie bilden eine Hierarchie; der
- mächtigere Typ schließt hierbei jeweils den (Wertebereich des) kleineren
- Typ(s) ein.
-
- LONGREAL J REAL J LONGINT J INTEGER J SHORTINT
-
- 6.2. Arraytypen
-
- Ein Array ist eine Datenstruktur, die aus einer festen Anzahl von Elementen des
- gleichen Typs, genannt Elementtyp, besteht. Als Länge des Arrays wird die
- Anzahl seiner Elemente bezeichnet. Die Elemente eines Arrays werden durch
- Indizes ausgewählt. Dies sind Integerzahlen im Wertebereich zwischen 0 und
- (Länge minus 1).
-
- $ ArrayType = ARRAY length {"," length} OF type.
- $ length = ConstExpression.
-
- Eine Deklaration der Form
-
- ARRAY N0, N1, ... , Nk OF T
-
- wird betrachtet als Abkürzung der Deklaration
-
- ARRAY N0 OF
- ARRAY N1 OF
- ...
- ARRAY Nk OF T
-
-
- Beispiele für Arraytypen:
-
- ARRAY N OF INTEGER
- ARRAY 10, 20 OF REAL
-
- 6.3. Recordtypen
-
- Ein Record ist eine Datenstruktur, die eine feste Anzahl von Elementen,
- möglicherweise unterschiedlicher Typen, beinhaltet. Bei der Deklaration eines
- Recordtyps wird für jedes Element, genannt Feld, sein Typ und der Name, der das
- Feld auswählt, festgelegt. Der Gültigkeitsbereich dieser Feldnamen ist die
- Recorddefinition; sie sind aber auch innerhalb von Feld-Bezeichnern (siehe 8.1)
- sichtbar, die sich auf Elemente von Recordvariablen beziehen.
-
- $ RecordType = RECORD ["(" BaseType ")"] FieldListSequence END.
- $ BaseType = qualident.
- $ FieldListSequence = FieldList {";" FieldList}.
- $ FieldList = [IdentList ":" type].
- $ IdentList = identdef {"," identdef}.
-
- Soll ein Recordtyp exportiert werden, so müssen diejenigen Feldnamen, die
- außerhalb des definierenden Moduls sichtbar sein sollen, markiert werden.
- Solcherart markierte Felder werden public genannt, nicht markierte hingegen
- private. Recordtypen sind erweiterbar, d.h. ein Recordtyp läßt sich als
- Erweiterung eines anderen Recordtyps vereinbaren. In den obigen Beispielen ist
- CenterNode eine (direkte) Erweiterung von Node, welches wiederum ein (direkter)
- Basistyp (Base Type) von CenterNode ist. Genauer gesagt, erweitert CenterNode
- den Typ Node um die Felder name und subnode.
-
- Definition: Ein Typ T0 erweitert einen Typ T, wenn er gleich T ist, oder wenn
- er die direkte Erweiterung einer Erweiterung von T darstellt. Umgekehrt ist
- ein Typ T ein Basistyp von T0, falls er gleich T0 ist, oder falls er der
- direkte Basistyp eines Basistyps von T0 ist.
-
- Beispiele für Recordtypen:
-
- RECORD
- day, month, year: INTEGER
- END
-
- RECORD
- name, firstname: ARRAY 32 OF CHAR;
- age: INTEGER;
- salary: REAL
- END
-
- 6.4. Pointertypen
-
- Variablen eines Pointertyps (Zeigertyps) P nehmen als Werte Referenzen auf
- Variablen eines Typs T an. Man sagt, der Pointertyp P ist an den Typ T
- gebunden, und T ist der Pointer-Basistyp von P. T muß ein Record- oder
- Arraytyp sein. Pointertypen erben die Erweiterungsbeziehungen ihrer Basistypen.
- Wenn ein Typ T0 eine Erweiterung von T ist, und P0 ein an T0 gebundener
- Pointertyp, dann ist P0 auch eine Erweiterung von P.
-
- $ PointerType = POINTER TO type.
-
- Ist p eine Variable vom Typ P = POINTER TO T, dann hat der Aufruf der
- vordefinierten Prozedur NEW(p) die folgende Wirkung (siehe 10.2): Im freien
- Speicherbereich wird eine Variable vom Typ T alloziert und eine Referenz auf
- diese Variable wird der Pointervariablen p zugewiesen. Die Pointervariable p
- ist vom Typ P; die referenzierte Variable p^ ist vom Typ T. Kann kein Speicher
- reserviert werden, so wird der Pointervariablen p der Wert NIL zugewiesen.
- Jeder Pointervariablen darf der Wert NIL zugewiesen werden, welcher auf keine
- Variable verweist.
-
- 6.5. Prozedurtypen
-
- Variablen eines Prozedurtyps T haben als Wert eine Prozedur. Wird
- eine Prozedur einer Prozedurvariablen vom Typ T zugewiesen, so müssen die
- (Typen der) formalen Parameter von P die gleichen sein, wie die der Parameter
- von T. Gleiches gilt für den Typ des Ergebnisses im Fall einer
- Funktionsprozedur (siehe 10.1). P darf nicht lokal zu einer anderen Prozedur
- vereinbart sein und darf auch keine vordefinierte Prozedur sein. Jeder
- Prozedurvariablen darf der Wert NIL zugewiesen werden, welcher auf keine
- Prozedur verweist.
-
- $ ProcedureType = PROCEDURE [FormalParameters].
-
-
- 7. Variablendeklarationen
-
- Variablendeklarationen dienen dazu, Variablen einzuführen und sie mit einem
- Namen zu verbinden, der im gegebenen Gültigkeitsbereich eindeutig sein muß.
- Variablendeklarationen dienen auch dazu, einen Datentyp mit der Variablen zu
- assoziieren.
-
- $ VariableDeclaration = IdentList ":" type.
-
- Variablen, deren Name in der selben Liste auftreten, haben alle den gleichen
- Typ.
-
- Beispiele für Variablendeklarationen (siehe Beispiele in Kap. 6):
-
- i, j, k: INTEGER
- x, y: REAL
- p, q: BOOLEAN
- s: SET
- f: Function
- a: ARRAY 100 OF REAL
- w: ARRAY 16 OF
- RECORD ch: CHAR;
- count: INTEGER
- END
- t: Tree
-
-
- 8. Ausdrücke
-
- Ausdrücke (Expressions) beschreiben die Rechenregeln, nach denen die Werte von
- Konstanten und die aktuellen Werte von Variablen kombiniert werden, um durch
- die Anwendung von Operatoren und Funktionsprozeduren neue Werte zu erhalten.
- Ausdrücke bestehen aus Operanden und Operatoren. Spezielle Assoziationen von
- Operatoren und Operanden lassen sich durch Klammerung ausdrücken.
-
-
- 8.1. Operanden
-
- Mit Ausnahme von Mengen und Literalen, d.h. Zahlen und Zeichenketten, werden
- Operanden durch Bezeichner (Designators) dargestellt. Ein Bezeichner besteht
- aus einem Namen, der sich auf eine zu bezeichnende Konstante, Variable oder
- Prozedur bezieht. Dieser Name kann durch einen Modulnamen qualifiziert werden
- (siehe Kap. 4 und 11), und von einem Selektor gefolgt werden, falls das
- bezeichnete Objekt Element einer Struktur ist.Falls A einen Array bezeichnet,
- dann bezieht sich A[E] auf dasjenige Element von A, dessen Index den aktuellen
- Wert des Ausdrucks E darstellt. Der Typ von E muß ein Integertyp sein. Ein
- Bezeichner der Form A[E1,E2, ... ,En] steht für A[E1][E2]...[En]. Falls p eine
- Pointervariable bezeichnet, dann bezieht sich p^ auf diejenige Variable, die
- von p referenziert wird. Bezeichnet r einen Record, dann bezieht sich r.f
- auf das Feld f des Records r. Falls p einen Pointer bezeichnet, dann bezieht
- sich p.f auf das Feld f des Records p^, d.h. der Punkt impliziert die
- Dereferenzierung und der Bezeichner steht für p^.f; sinngemäß bezeichnet p[E]
- das Element von p^ mit dem Index E.Der Type Guard v(T0), stellt sicher, daß v
- vom Typ T0 ist (siehe Kap. 6), d.h. das Programm wird abgebrochen, falls v
- nicht vom Typ T0 ist. Ein Type Guard ist anwendbar, falls 1. T0 eine
- Erweiterung des deklarierten Typs T von v ist, und falls 2. v ein
- Variablenparameter (s.u.) eines Recordtyps ist, oder v eine Pointervariable
- darstellt.
-
- $ designator = qualident {"." ident | "[" ExpList "]" |
- $ "(" qualident ")" | "^" }.
- $ ExpList = expression {"," expression}.
-
- Ist das bezeichnete Objekt eine Variable, so bezieht sich der Bezeichner auf
- den aktuellen Wert der Variablen. Ist das Objekt eine Prozedur, dann bezieht
- sich ein Bezeichner ohne Parameterliste auf diese Prozedur. Wird er von einer
- (möglicherweise leeren) Parameterliste gefolgt, dann impliziert der Bezeichner
- eine Aktivierung der Prozedur und steht für den Wert, der aus ihrer Ausführung
- resultiert. Die (Typen der) aktuellen Parameter müssen denen der formalen
- Parameter entsprechen, so wie sie bei der Definition der Prozedur spezifiziert
- wurden (siehe Kap. 10).
-
- Beispiele für Bezeichner (siehe Beispiele in Kap. 7):
-
- i (INTEGER)
- a[i] (REAL)
- w[3].ch (CHAR)
- t.key (INTEGER)
- t.left.right (Tree)
- t(CenterNode).subnode (Tree)
-
- 8.2. Operatoren
-
- Die Syntax von Ausdrücken unterscheidet zwischen vier Klassen von Operatoren
- mit verschiedenen Präzedenzen (Bindungßtärken). Der Operator ~ hat die höchste
- Präzedenz, gefolgt von den Multiplikationsoperatoren, Additionsoperatoren und
- Relationen. Operatoren der gleichen Präzedenzstufe binden von links nach
- rechts.
-
- Beispiel:
-
- x-y-z steht für (x-y)-z.
-
- $ expression = SimpleExpression [relation SimpleExpression].
- $ relation = "=" | "#" | "<" | "<=" | ">" | ">=" | IN | IS.
- $ SimpleExpression = ["+"|"-"] term {AddOperator term}.
- $ AddOperator = "+" | "-" | OR .
- $ term = factor {MulOperator factor}.
- $ MulOperator = "*" | "/" | DIV | MOD | "&" .
- $ factor = number | CharConstant | string | NIL | set |
- $ designator [ActualParameters] | "(" expression ")" | "~" factor.
- $ set = "{" [element {"," element}] "}".
- $ element = expression [".." expression].
- $ ActualParameters = "(" [ExpList] ")" .
-
- Die in Oberon verfügbaren Operatoren sind in den folgenden Tabellen aufgeführt.
- Manchmal werden verschiedene Operationen durch das gleiche Operatorsymbol
- gekennzeichnet; in diesen Fällen wird die tatsächliche Operation durch den Typ
- der Operanden bestimmt.
-
- 8.2.1. Logische Operatoren
-
- Symbol Ergebnis
-
- OR logische Disjunktion
- & logische Konjunktion
- ~ Negation
-
- Diese Operatoren sind auf BOOLEAN-Operanden anwendbar und liefern
- ein Ergebnis vom Typ BOOLEAN.
-
- p OR q steht für "wenn p, dann TRUE, sonst q"
- p & q steht für "wenn p, dann q, sonst FALSE"
- ~ p steht für "nicht p"
-
- 8.2.2. Arithmetische Operatoren
-
- Symbol Ergebnis
-
- + Summe
- - Differenz
- * Produkt
- / Quotient
- DIV ganzzahliger Quotient
- MOD Modulus
-
- Die Operatoren +, -, * und / beziehen sich auf Operanden numerischer Typen.
- Der Typ des Ergebnisses ist derjenige Operandentyp, der den Typ des anderen
- Operanden einschließt, außer bei der Division (/), bei der das Ergebnis
- derjenige Realtyp ist, welcher beide Operandentypen einschließt. Als
- monadische Operatoren bezeichnen - die Vorzeichenumkehr und + die Identität.
- Die Operatoren DIV und MOD sind nur auf ganzzahlige Operanden anwendbar. Sie
- sind durch die folgenden Beziehungen zwischen beliebigem x und y>0 definiert:
-
- x = (x DIV y) * y + (x MOD y)
- 0 <= (x MOD y) < y
-
- 8.2.3. Mengenoperatoren
-
- Symbol Ergebnis
-
- + Vereinigungsmenge
- - Differenzmenge
- * Schnittmenge
- / symmetrische Mengendifferenz
-
- Das monadische Minuszeichen bezeichnet das Mengenkomplement von x, d.h. -x
- bezeichnet die Menge der Integerzahlen zwischen 0 und MAX(SET), die nicht
- Elemente von x sind.
-
- x - y = x * (-y)
- x / y = (x-y) + (y-x)
-
- 8.2.4. Relationen
-
- Symbol Relation
-
- = gleich
- # ungleich
- < kleiner
- <= kleiner oder gleich
- > größer
- >= größer oder gleich
- IN Mengenzugehörigkeit
- IS Typtest
-
- Relationen liefern Ergebnisse vom Typ BOOLEAN. Die Ordnungsrelationen <, <=, >
- und >= sind anwendbar auf numerische Typen, CHAR und Zeichenarrays (Strings).
- Die Relationen = und # sind auch auf BOOLEAN, Mengen-, Pointer- und
- Prozedurtypen anwendbar. x IN s steht für "x ist Element von s". x muß dabei
- ein Integertyp sein und s vom Typ SET. v IS T steht für "v ist vom Typ T" und
- wird Typtest genannt. Er ist anwendbar, falls 1. T eine Erweiterung des
- deklarierten Typs T0 von v ist, und falls 2. v ein Variablenparameter eines
- Recordtyps ist, oder v eine Pointervariable ist. Nehmen wir z.B. an, daß T
- eine Erweiterung von T0 darstellt und daß v ein als vom Typ T0 deklarierter
- Bezeichner ist, dann bestimmt das Ergebnis des Tests "v IS T", ob die aktuell
- bezeichnete Variable (nicht nur vom Typ T0, sondern auch) vom Typ T ist. Der
- Wert von "NIL IS T" ist nicht definiert.
-
- Beispiele für Ausdrücke (siehe Beispiele in Kap. 7):
-
- 1987 (INTEGER)
- i DIV 3 (INTEGER)
- ~p OR q (BOOLEAN)
- (i+j) * (i-j) (INTEGER)
- s - {8, 9, 13} (SET)
- i + x (REAL)
- a[i+j] * a[i-j] (REAL)
- (0<=i) & (i<100) (BOOLEAN)
- t.key = 0 (BOOLEAN)
- k IN {i .. j-1} (BOOLEAN)
- t IS CenterNode (BOOLEAN)
-
- 9. Anweisungen
-
- Anweisungen (Statements) bezeichnen Aktionen. Wir unterscheiden zwischen
- elementaren und strukturierten Anweisungen. Elementare Anweisungen bestehen
- nicht selber wieder aus Anweisungen. Es sind dies Wertzuweisungen,
- Prozeduraufrufe, und die RETURN- und EXIT-Anweisungen. Strukturierte
- Anweisungen beinhalten selbst wieder Anweisungen. Sie werden verwendet, um
- Anweisungsfolgen (Statement Sequences), Bedingungen, selektive und wiederholte
- Anweisungen zum Ausdruck zu bringen. Ein Anweisung kann auch leer sein; in
- diesem Fall bezeichnet sie keine Aktion. Die leere Anweisung dient dem Zweck,
- die Interpunktionsregeln in Anweisungsfolgen zu vereinfachen.
-
- $ statement = [assignment | ProcedureCall |
- $ IfStatement | CaseStatement | WhileStatement | RepeatStatement |
- $ LoopStatement | WithStatement | EXIT | RETURN [expression] ].
-
- 9.1. Wertzuweisungen
-
- Eine Wertzuweisung (Assignment) wird verwendet, um den aktuellen Wert einer
- Variablen durch einen neuen Wert zu ersetzen, welcher durch einen Ausdruck
- angegeben wird. Der Zuweisungsoperator wird geschrieben als ":=" und gesprochen
- als "wird zu".
-
- $ assignment = designator ":=" expression.
-
- Der Typ des Ausdrucks muß im Typ der Variablen eingeschlossen sein, oder er
- muß den Typ der Variablen erweitern. Dabei gelten die folgenden Ausnahmen:
-
- 1. Die Konstante NIL darf Variablen eines beliebigen Pointer- oder
- Prozedurtyps zugewiesen werden.
-
- 2. Strings können jeder Variablen eines Zeichenarray-Typs zugewiesen werden,
- vorausgesetzt die Länge des Strings ist kleiner als die Länge des Arrays.
-
- Wird ein String s der Länge n einem Array a zugewiesen, dann ist das
- Ergebnis a[i] = s[i] für i = 0..n-1 und a[n] = 0X.
-
- 3. Werte vom Typ CHAR und SHORTINT dürfen Variablen vom Typ BYTE zugewiesen
- werden.
-
- Beispiele für Wertzuweisungen (siehe auch Beispiele in Kap. 7):
-
- i := 0
- p := i = j
- x := i + 1
- k := log2(i+j)
- F := log2
- s := {2, 3, 5, 7, 11, 13}
- a[i] := (x+y) * (x-y)
- t.key := i
- w[i+1].ch := "A"
-
- 9.2. Prozeduraufrufe
-
- Ein Prozeduraufruf dient dazu, eine Prozedur zu aktivieren. Der Prozeduraufruf
- kann eine Liste von Parametern enthalten, welche anstelle der
- korrespondierenden formalen Parameter eingesetzt werden, die bei der Definition
- der Prozedur angegeben wurden (siehe Kap. 10). Der Zusammenhang zwischen
- aktuellen und formalen Parametern wird durch die Position in der jeweiligen
- Liste hergestellt. Es existieren zwei Arten von Parametern:
- Variablenparameter und Wertparameter.Im Fall des Variablenparameter muß der
- aktuelle Parameter ein Bezeichner sein, der eine Variable repräsentiert.
- Bezeichnet er ein Element einer strukturierten Variablen, so wird der Selektor
- ausgewertet, wenn die Substitution formaler/aktueller Parameter stattfindet,
- d.h. vor der Ausführung der Prozedur. Ist der Parameter ein Wertparameter, dann
- muß der korrespondierende aktuelle Parameter ein Ausdruck sein. Dieser
- Ausdruck wird vor der Aktivierung der Prozedur evaluiert und das Ergebnis dem
- formalen Parameter zugewiesen, der nun eine lokale Variable darstellt (siehe
- auch 10.1).
-
- $ ProcedureCall = designator [ActualParameters].
-
- Beispiele für Prozeduraufrufe:
-
- ReadInt(i) (siehe Kap. 10)
- WriteInt(j*2+1, 6)
- INC(w[k].count)
-
- 9.3. Anweisungsfolgen
-
- Anweisungsfolgen bezeichnen Sequenzen von Aktionen und werden durch die
- entsprechenden Einzelanweisungen, getrennt durch Strichpunkte, spezifiziert.
-
- $ StatementSequence = statement {";" statement}.
-
- 9.4. If-Anweisungen
-
- $ IfStatement = IF expression THEN StatementSequence
- $ {ELSIF expression THEN StatementSequence}
- $ [ELSE StatementSequence]
- $ END.
-
- If-Anweisungen bezeichnen die bedingte Ausführung von Anweisungen. Der
- boolesche Ausdruck vor einer bedingten Anweisung wird Guard genannt. Die
- einzelnen Guards werden nacheinander in der Reihenfolge ihres Auftretens
- ausgewertet, bis die Auswertung eines dieser Guards den Wert TRUE ergibt; dann
- wird die damit verbundene Anweisungsfolge ausgeführt. Ist keiner der Guards
- erfüllt, dann wird die nach dem Symbol ELSE stehende Anweisungsfolge ausgeführt,
- sofern eine vorhanden ist.
-
- Beispiel:
-
- IF (ch >= "A") & (ch <= "Z") THEN ReadIdentifier
- ELSIF (ch >= "0") & (ch <= "9") THEN ReadNumber
- ELSIF ch = 22X THEN ReadString
- ELSE SpecialCharacter
- END
-
- 9.5. Case-Anweisungen
-
- Case-Anweisungen bezeichnen die Auswahl und Ausführung von Anweisungsfolgen
- entsprechend dem Wert eines Ausdrucks. Zuerst wird der Ausdruck berechnet,
- dann wird diejenige Anweisungsfolge ausgeführt, deren Liste von Case-Labels
- den berechneten Wert enthält. Der Case-Ausdruck und alle Case-Labels müssen
- vom gleichen Typ sein, der ein Integertyp oder CHAR sein muß. Case-Labels sind
- Konstanten, und kein Wert darf mehr als einmal auftreten. Falls der Wert des
- Ausdrucks nicht als Case-Label auftritt, so wird die Anweisungsfolge nach dem
- Symbol ELSE ausgeführt, sofern vorhanden; andernfalls liegt ein Laufzeitfehler
- vor.
-
- $ CaseStatement = CASE expression OF case {"|" case}
- $ [ELSE StatementSequence] END.
- $ case = [CaseLabelList ":" StatementSequence].
- $ CaseLabelList = CaseLabels {"," CaseLabels}.
- $ CaseLabels = ConstExpression [".." ConstExpression].
-
- Beispiel:
-
- CASE ch OF
- "A" .. "Z": ReadIdentifier
- | "0" .. "9": ReadNumber
- | 22X : ReadString
- ELSE SpecialCharacter
- END
-
- 9.6. While-Anweisungen
-
- While-Anweisungen bezeichnen Wiederholungen. Falls der boolesche Ausdruck
- (Guard) den Wert TRUE ergibt, so wird die Anweisungsfolge ausgeführt. Die
- Berechnung des Ausdrucks und die Ausführung der Anweisungsfolge werden so lange
- wiederholt, wie der boolesche Ausdruck das Ergebnis TRUE liefert.
-
- $ WhileStatement = WHILE expression DO StatementSequence END.
-
- Beispiele:
-
- WHILE j > 0 DO
- j := j DIV 2; i := i+1
- END
-
- WHILE (t # NIL) & (t.key # i) DO
- t := t.left
- END
-
- 9.7. Repeat-Anweisungen
-
- Eine Repeat-Anweisung bezeichnet die wiederholte Ausführung einer
- Anweisungsfolge, solange bis eine Bedingung erfüllt ist. Die Anweisungsfolge
- wird mindestens einmal ausgeführt.
-
- $ RepeatStatement = REPEAT StatementSequence UNTIL expression.
-
- 9.8. Loop-Anweisungen
-
- Eine Loop-Anweisung bezeichnet die wiederholte Ausführung einer
- Anweisungsfolge. Dies wird durch die Ausführung einer beliebigen Exit-Anweisung
- innerhalb der Anweisungsfolge beendet (siehe auch 9.9).
-
- $ LoopStatement = LOOP StatementSequence END.
-
- Beispiel:
-
- LOOP
- IF t1 = NIL THEN EXIT END ;
- IF k < t1.key THEN t2 := t1.left; p := TRUE
- ELSIF k > t1.key THEN t2 := t1.right; p := FALSE
- ELSE EXIT
- END ;
- t1 := t2
- END
-
- Obwohl While- und Repeat-Anweisungen durch eine LOOP-Anweisung mit einer
- einzelnen Exit-Anweisung ausgedrückt werden können, wird die Verwendung von
- While- und Repeat-Anweisungen in den sehr häufig auftretenden Situation
- empfohlen, in denen der Abbruch von einer einzigen Bedingung am Anfang oder
- Ende der wiederholten Anweisungsfolge abhängt. Die Loop-Anweisung ist
- nützlich, um Fälle mit mehreren Abbruchbedingungen und -punkten auszudrücken.
-
- 9.9. Return- und Exit-Anweisungen
-
- Eine Return-Anweisung besteht aus dem Symbol RETURN, möglicherweise gefolgt von
- einem Ausdruck. Sie zeigt die Beendigung einer Prozedur an, bei
- Funktionsprozeduren bestimmt der auf das RETURN folgende Ausdruck das Resultat.
- In diesem Fall muß der Typ des Ausdrucks gleich dem Ergebnistyp sein, wie er
- im Prozedurkopf angegeben wurde (siehe Kap.10).Funktionsprozeduren verlangen
- die Anwesenheit einer Return-Anweisung, welche den Resultatwert angibt. Mehrere
- Return-Anweisungen sind erlaubt, obwohl nur eine davon ausgeführt wird. Bei
- reinen Prozeduren impliziert das Ende des Prozedurkörpers ein Return-Anweisung.
- Eine ausdrückliche Return-Anweisung erscheint daher als zusätzlicher
- (möglicherweise außerordentlicher) Abschlußpunkt der Prozedur. Eine
- Exit-Anweisung besteht aus dem Symbol EXIT. Sie bestimmt die Beendigung der
- umschließenden Loop-Anweisung. Das Programm wird mit derjenigen Anweisung
- fortgesetzt, die auf die Loop-Anweisung folgt. Exit-Anweisungen sind textuell,
- aber nicht syntaktisch, an diejenige Loop-Anweisung gebunden, in der sie
- enthalten sind.
-
- 9.10. With-Anweisungen
-
- Eine Pointervariable oder ein Variablenparameter mit Recordstruktur vom Typ T0
- darf im Kopf einer With-Anweisung mit einem Typ T angegeben werden, der eine
- Erweiterung des Typs T0 darstellt. Dann wird diese Variable innerhalb der
- With-Anweisung so behandelt, als ob sie vom Typ T vereinbart wäre. Die
- With-Anweisung übernimmt eine Rolle ähnlich dem Type Guard, nur daß sie diesen
- Guard über eine Anweisungsfolge ausdehnt. Sie kann deshalb als ein regionaler
- Type Guard betrachtet werden.
-
- $ WithStatement = WITH qualident ":" qualident DO StatementSequence END.
-
- Beispiel:
-
- WITH t: CenterNode DO name := t.name; L := t.subnode END
-
-
- 10. Prozedurdeklarationen
-
- Prozedurdeklarationen bestehen aus einem Prozedurkopf (Procedure Heading) und
- einem Prozedurkörper (Procedure Body). Der Prozedurkopf bestimmt den
- Prozedurnamen, die formalen Parameter und den Typ des Ergebnisses (sofern
- vorhanden). Der Prozedurkörper beinhaltet Deklarationen und Anweisungen. Der
- Prozedurname wird am Ende der Prozedurdeklaration wiederholt.Es gibt zwei Arten
- von Prozeduren, reine Prozeduren und Funktionsprozeduren. Letztere werden
- durch Funktionsbezeichner als Bestandteile von Ausdrücken aktiviert und liefern
- Ergebnisse, welche als Operanden in diese Ausdrücke einfließen. Reine
- Prozeduren werden durch Prozeduraufrufe aktiviert. Funktionsprozeduren werden
- bei der Deklaration durch die Angabe eines Ergebnistyps nach der Parameterliste
- unterschieden; ihr Prozedurkörper muß eine RETURN-Anweisung enthalten, welche
- das Ergebnis bestimmt.Alle Konstanten, Variablen, Typen und Prozeduren, die
- innerhalb des Prozedurkörpers vereinbart werden, sind lokal zu dieser Prozedur.
- Die Werte lokaler Variablen sind bei Eintritt in die Prozedur unbestimmt. Da
- auch Prozeduren als lokale Objekte vereinbart werden dürfen, kann man
- Prozedurdeklarationen ineinander verschachteln.Zusätzlich zu den formalen
- Parametern und lokal vereinbarten Objekten sind auch die in der Umgebung der
- Prozedur vereinbarten Objekte innerhalb der Prozedur sichtbar (mit Ausnahme
- derjenigen Objekte, die den gleichen Namen tragen, wie lokale Objekte). Die
- Verwendung des Prozedurnamens als Aufruf innerhalb ihrer Deklaration impliziert
- eine rekursive Aktivierung der Prozedur.
-
- $ ProcedureDeclaration = ProcedureHeading ";" ProcedureBody ident.
- $ ProcedureHeading = PROCEDURE ["*"] identdef [FormalParameters].
- $ ProcedureBody = DeclarationSequence [BEGIN StatementSequence] END.
- $ ForwardDeclaration = PROCEDURE "^" identdef [FormalParameters].
- $ DeclarationSequence = {CONST {ConstantDeclaration ";"} |
- $ TYPE {TypeDeclaration ";"} | VAR {VariableDeclaration ";"}}
- $ {ProcedureDeclaration ";" | ForwardDeclaration ";"}.
-
- Eine Vorausdeklaration erlaubt es, sich auf eine Prozedur zu beziehen, die erst
- später im Text vollständig vereinbart wird. Die tatsächliche Deklaration, die
- den Prozedurkörper bestimmt, muß die gleichen Parameter und den gleichen
- Ergebnistyp (sofern vorhanden) wie die Vorausdeklaration besitzen, und muß im
- gleichen Gültigkeitsbereich liegen. Ein dem PROCEDURE-Symbol folgender Stern
- ist ein Hinweis an den Compiler, der anzeigt, daß die Prozedur als Parameter
- verwendbar ist und Variablen kompatibler Prozedurtypen zugewiesen werden kann.
-
- 10.1. Formale Parameter
-
- Formale Parameter sind Namen, welche die aktuellen Parameter einer Prozedur
- repräsentieren. Der Zusammenhang zwischen aktuellen und formalen Parametern
- wird beim Aufruf der Prozedur hergestellt. Es gibt zwei Arten von Parametern,
- Wertparameter (Value Parameters) und Variablenparameter (Variable Parameters).
- Die jeweilige Art wird in der formalen Parameterliste angegeben. Wertparameter
- stehen für lokale Variablen, denen das Ergebnis der Auswertung des
- korrespondierenden aktuellen Parameter als Anfangswert zugewiesen wird.
- Variablenparameter entsprechen aktuellen Parametern, welche Variablen sind, und
- repräsentieren diese. Variablenparameter werden durch das Symbol VAR
- gekennzeichnet, Wertparameter durch dessen Abwesenheit. Funktionsprozeduren
- ohne Parameter müssen eine leere Parameterliste besitzen und müssen mit einem
- Funktionsbezeichner aufgerufen werden, dessen aktuelle Parameterliste ebenfalls
- leer ist. Formale Parameter sind lokal zur Prozedur, d.h. ihr
- Gültigkeitsbereich ist der Text der Prozedurdeklaration.
-
- $ FormalParameters = "(" [FPSection {";" FPSection}] ")" [":" qualident].
- $ FPSection = [VAR] ident {"," ident} ":" FormalType.
- $ FormalType = {ARRAY OF} qualident.
-
- Der Typ jedes formalen Parameters wird in der Parameterliste angegeben. Bei
- Variablenparametern muß er identisch dem Typ des entsprechenden aktuellen
- Parameters sein, außer im Fall eines Records; hier muß er ein Basistyp des
- Typs des entsprechenden aktuellen Parameters sein. Bei Wertparametern gelten
- die Regeln der Zuweisungskompatibilität (siehe 9.1). Wird ein Parametertyp
- angegeben als ARRAY OF Tdann nennt man den Parameter einen Open Array Parameter
- und der entsprechende aktuelle Parameter darf irgend ein Array vom Elementtyp T
- sein.Im Falle eines Parameters vom formalen Typ BYTE darf der entsprechende
- aktuelle Parameter auch vom Typ CHAR oder SHORTINT sein. Ist der Typ des
- formalen Variablenparameters ein ARRAY OF BYTE, dann sind aktuelle Parameter
- jeden beliebigen Typs zugelassen. Spezifiziert der formale Parameter einen
- Prozedurtyp, dann muß der korrespondierende aktuelle Parameter entweder eine
- auf der Stufe 0 vereinbarte Prozedur sein, oder eine Variable (oder ein
- Parameter) von diesem Prozedurtyp sein. Eine vordefinierte Prozedur ist an
- dieser Stelle nicht erlaubt. Das Ergebnis einer Prozedur darf weder ein Record
- noch ein Array sein.
-
- Beispiele für Prozedurdeklarationen:
-
- PROCEDURE ReadInt(VAR x: INTEGER);
- VAR i : INTEGER; ch: CHAR;
- BEGIN i := 0; Read(ch);
- WHILE ("0" <= ch) & (ch <= "9") DO
- i := 10*i + (ORD(ch)-ORD("0")); Read(ch)
- END ;
- x := i
- END ReadInt
-
- PROCEDURE WriteInt(x: INTEGER); (* 0 <= x < 10^5 *)
- VAR i: INTEGER;
- buf: ARRAY 5 OF INTEGER;
- BEGIN i := 0;
- REPEAT buf[i] := x MOD 10; x := x DIV 10; INC(i) UNTIL x = 0;
- REPEAT DEC(i); Write(CHR(buf[i] + ORD("0"))) UNTIL i = 0
- END WriteInt
-
- PROCEDURE log2(x: INTEGER): INTEGER;
- VAR y: INTEGER; (*assume x>0*)
- BEGIN y := 0;
- WHILE x > 1 DO x := x DIV 2; INC(y) END ;
- RETURN y
- END log2
-
- 10.2. Vordefinierte Prozeduren
-
- Die folgende Tabelle zeigt die vordefinierten Prozeduren auf. Einige davon
- sind generische Prozeduren, d.h. sie sind auf mehrere Operandentypen anwendbar.
- v steht für eine Variable, x und n stehen für Ausdrücke und T für irgendeinen
- Typ.
-
- Funktionsprozeduren:
-
- Name Argumenttyp Ergebnistyp Funktion
-
- ABS(x) numerischer Typ Typ von x Absolutwert
- ODD(x) Integertyp BOOLEAN x MOD 2 = 1
- CAP(x) CHAR CHAR entsprechender Großbuchstabe
- ASH(x, n) x, n: Integertyp LONGINT x * 2n, arithmetischer Shift
- LEN(v, n) v: Array LONGINT Länge von v in Dimension n
- n: Integertyp LEN(v) ist äquivalent zu
- LEN(v, 0)
- SIZE(T) beliebiger Typ Integertyp Anzahl der von T beanspruchten Bytes
- MAX(T) T = Grundtyp T Maximalwert des Typs T
- T = SET INTEGER größtes Element der Menge
- MIN(T) T = Grundtyp T Minimalwert des Typs T
- T = SET INTEGER 0
-
- Prozeduren zur Typkonversion:
-
- Name Argumenttyp Ergebnistyp Funktion
-
- ORD(x) CHAR, BYTE INTEGER Ordinalzahl von x
- CHR(x) Integertyp, BYTE CHAR Zeichen mit dem Ordinalzahl x
- SHORT(x) LONGINT INTEGER Identität
- INTEGER SHORTINT
- LONGRAL REAL (Beschneidung des Wertes möglich)
- LONG(x) SHORTINT INTEGER Identität
- INTEGER LONGINT
- REAL LONGREAL
- ENTIER(x) reeller Typ LONGINT größte Integerzahl <= x
- Anmerkung: ENTIER(i/j) = i DIV j
-
- Reine Prozeduren:
-
- Name Argumenttyp Funktion
-
- INC(v) Integertyp v := v+1
- INC(v, x) Integertyp v := v+x
- DEC(v) Integertyp v := v-1
- DEC(v, x) Integertyp v := v-x
- INCL(v, x) v: SET; x: Integertyp v := v + {x}
- EXCL(v, x) v: SET; x: Integertyp v := v - {x}
- COPY(x, v) x: Zeichenarray, String v := x
- v: Zeichenarray
- NEW(v) Pointertyp Speicher für v^ reservieren
- HALT(x) Integerkonstante Programmlauf beenden
-
- Der zweite Parameter von INC und DEC kann entfallen, dann wird jeweils der Wert
- 1 verwendet. Die Interpretation des Parameters x in HALT(x) wird der
- jeweiligen Systemimplementation überlassen.
-
-
- 11. Module
-
- Ein Modul besteht aus einer Sammlung von Konstanten-, Typen-, Variablen- und
- Prozedurdeklarationen und aus einer Folge von Anweisungen zur Initialisierung
- von Variablen. Ein Modul besteht typischerweise aus einem Text, der als
- Einheit kompilerbar ist.
-
- $ module = MODULE ident ";" [ImportList] DeclarationSequence
- $ [BEGIN StatementSequence] END ident "." .
- $ ImportList = IMPORT import {"," import} ";" .
- $ import = ident [":=" ident].
-
- Die Importliste gibt diejenigen Module an, deren Klient das aktuelle Modul ist.
- Wird ein Name x von einem Modul M exportiert, und wird M in der Importliste
- eines anderen Moduls aufgeführt, dann wird x dort als M.x referenziert. Falls
- in der Importliste die Form "M := M1" verwendet wird, so wird auf ein im Modul
- M1 deklariertes Objekt x als M.x zugegriffen.Namen, die in einem Klientenmodul
- sichtbar sein sollen, also außerhalb des vereinbarenden Moduls, müssen bei
- ihrer Deklaration mit einer Exportmarke versehen werden. Die Anweisungsfolge
- nach dem Symbol BEGIN wird ausgeführt, wenn das Modul geladen wird. Einzelne
- (parameterlose) Prozeduren können anschließend vom System aktiviert werden,
- sie dienen als Kommandos (Commands).
-
- Beispiel:
-
- MODULE Out;
- (*exported procedures: Write, WriteInt, WriteLn*)
- IMPORT Texts, Oberon;
-
- VAR W: Texts.Writer;
-
- PROCEDURE Write*(ch: CHAR);
- BEGIN
- Texts.Write(W, ch)
- END;
-
- PROCEDURE WriteInt*(x, n: LONGINT);
- VAR
- i: INTEGER;
- a: ARRAY 16 OF CHAR;
- BEGIN
- i := 0;
- IF x < 0 THEN Texts.Write(W, "-"); x := -x END ;
- REPEAT a[i] := CHR(x MOD 10 + ORD("0")); x := x DIV 10; INC(i) UNTIL x = 0;
- REPEAT Texts.Write(W, " "); DEC(n) UNTIL n <= i;
- REPEAT DEC(i); Texts.Write(W, a[i]) UNTIL i = 0
- END WriteInt;
-
- PROCEDURE WriteLn*;
- BEGIN
- Texts.WriteLn(W);
- Texts.Append(Oberon.Log, W.buf)
- END WriteLn;
-
- BEGIN
- Texts.OpenWriter(W)
- END Out.
-
-
- Anhang: Das Modul SYSTEM
-
- Das Modul SYSTEM enthält bestimmte Prozeduren, welche notwendig sind, um
- "low-level"-Operationen zu programmieren, die sich direkt auf Objekte beziehen,
- die für einen bestimmten Computer oder ein spezielles Betriebssystem spezifisch
- sind. Dies beinhaltet beispielsweise Möglichkeiten zum Zugriff auf
- Peripheriegeräte, die direkt von diesem Computer kontrolliert werden und
- Möglichkeiten, die Typkompatibilitätsregeln zu durchbrechen, die sonst aufgrund
- der Sprachdefinition aufgezwungen werden. Es wird empfohlen, die Verwendung
- des Moduls SYSTEM auf spezielle Module (sogenannte Low-Level-Module) zu
- beschränken. Derartige Module sind naturgemäß nicht portabel, aber leicht am
- Namen SYSTEM in der Importliste erkennbar. Die folgenden Spezifikationen
- gelten für die ETH-Implementation für den NS32000-Prozessor. Die im Modul
- SYSTEM enthaltenen Prozeduren sind in den folgenden Tabellen aufgeführt.
- Sie entsprechen einzelnen Prozessorinstruktionen, die als Inline-Code
- kompiliert werden. Für weitere Details wird der Leser auf das
- Prozessorhandbuch verwiesen. v steht für eine Variable, x, y, a und n stehen
- für Ausdrücke und T steht für einen Typ.
-
- Funktionsprozeduren:
-
- Name Argumenttyp Ergebnistyp Funktion
-
- ADR(v) beliebig LONGINT Adresse der Variablen v
- BIT(a, n) a: LONGINT BOOLEAN Mem[a][n]
- n: Integertyp
- CC(n) n: Integerkonstante BOOLEAN Condition Code n (0 <= n < 16)
- LSH(x,
-
- LSH(x,n) x, n: Integertyp LONGINT logischer Shift
- ROT(x,n) x, n: Integertyp LONGINT Rotation
- VAL(T,x) T, x: beliebiger Typ T x interpretiert als vom Typ T
-
-
- Reine Prozeduren:
-
- Name Argumenttyp Funktion
-
- GET(a, v) a: LONGINT; v := Mem[a]
- v: beliebiger Grundtyp
- PUT(a, x) a: LONGINT; Mem[a] := x
- x: beliebiger Grundtyp
- MOVE(a0, a1, n) a0, a1, n: Integertyp Mem[a1+i] := Mem[a0+i], i = 0..n-1
- NEW(v, n) v: beliebiger Pointertyp reserviert einen Speicherblock von n
- n: Integertyp Bytes und übergibt seine Adresse an v
-
-
- Übersetzung aus dem Englischen: Michael Franz
-
-