Logo

Marco Cantù's
Essential Pascal

Kapitel 2
In Pascal codieren

Bevor wir mit dem eigentlichen Thema beginnen, dem Schreiben von Anweisungen in der Sprache Pascal, ist es wichtig, einige Elemente des Pascal-Codierstils zu beleuchten. Die Frage, um die es hier geht ist folgende: Wie sollten Sie, neben den Syntaxregeln, den Code schreiben? Es existiert auf diese Frage keine einfache Antwort, da der persönliche Geschmack unterschiedliche Stile diktieren kann. Es gibt jedoch einige Prinzipien bezüglich Kommentaren, Groß- und Kleinschreibung, Leerzeichen und der sogenannten Code-Einrückung, die Sie kennen sollten. Allgemein ist Übersichtlichkeit das Ziel eines jeden Codierstils. Der Stil und die Formatierungsentscheidungen, die Sie treffen, sind eine Form der Kurzschreibweise, die den Zweck eines bestimmten Code-Abschnitts kennzeichnen. Das wichtigste Werkzeug für die Übersichtlichkeit ist jedoch die Einheitlichkeit - welchen Stil Sie auch wählen, behalten Sie ihn innerhalb eines Projekts stets bei.

Kommentare

In Pascal werden Kommentare entweder in geschweiften Klammern, oder in einfachen Klammern mit nachfolgendem Stern eingeschlossen. Delphi akzeptiert auch Kommentare im C++ Stil, die bis zum Ende der Zeile gelten:

{ das ist ein Kommentar }
(* dies ist ein anderer Kommentar *)
// dies ist ein Kommentar bis ans Ende der Zeile

Die erste Form ist kürzer und wird häufiger verwendet. Die zweite Form wurde oft in Europa bevorzugt, da vielen Europäische Tastaturen das geschweifte Klammernsymbol fehlte. Die dritte Form des Kommentars wurde von C++ übernommen und ist nur in den 32-Bit Versionen von Delphi verfügbar. Kommentare, die bis zum Ende der Zeile gelten sind sehr nützlich für kurze Kommentare und für das "Auskommentieren" einer Code-Zeile.

In den Quelltexten zu diesem Buch werde ich versuchen, Kommentare in Kursiv (und Schlüsselwörter in Fettschrift) zu markieren, um mit der der Vorgabeeinstellung von Delphi's Syntaxhervorhebung übereinzustimmen.

Die Verfügbarkeit von drei unterschiedlichen Formen von Kommentaren kann nützlich sein, um verschachtelte Kommentare zu erzeugen. Wenn Sie mehrere Code-Zeilen auskommentieren möchten, um diese zu unterdrücken, und diese Zeilen ihrerseits einige echte Kommentare enthalten, so können Sie nicht die gleiche Kommentarform verwenden:

{  ... code
{ Kommentar, der Probleme erzeugt }
... code }

Mit einem anderen Kommentartyp können Sie den folgenden Code schreiben, der korrekt ist:

{  ... code
//dieser Kommentar ist OK
... code }

Beachten Sie, dass eine öffnende geschweifte Klammer oder Klammer-Stern, gefolgt von einem Dollar-Zeichen ($) eine Compiler-Direktive wird, wie z.B in {$X-}.

Tatsächlich sind Compiler-Direktiven immer noch Kommentare. Beispielsweise ist {$X+ Das ist ein Kommentar } zulässig. Es ist sowohl eine gültige Compiler-Direktive als auch ein Kommentar, obwohl vernünftige Programmierer wahrscheinlich dazu tendieren werden, Compiler-Direktiven und Kommentare zu trennen.

Verwendung der Groß- und Kleinschreibung

Der Pascal-Compiler ignoriert (im Gegensatz zu anderen Sprachen) die Groß- und Kleinschreibung (Capitalization) von Zeichen. Daher sind die Bezeichner Myname, MyName, myname, myName und MYNAME vollständig gleichbedeutend. Im allgemeinen ist das ein Vorteil, da viele Syntaxfehler in Sprachen, die die Groß- und Kleinschreibung unterschieden, durch eine falsche Schreibweise verursacht werden.

Hinweis: Es existiert nur eine Ausnahme für die Groß-Kleinschreibungsregel in Pascal: Die Prozedur Register in einer Komponentenbibliothek (Package) muss aus Gründen der Kompatibilität mit dem C++Builder mit einem großen R beginnen.

Es existieren jedoch auch einige subtile Nachteile. Zunächst müssen Sie erkennen, dass diese Bezeichner wirklich die selben sind, daher müssen Sie vermeiden, diese als unterschiedliche Elemente zu verwenden. Zweitens sollten Sie bemüht sein, die großgeschriebenen Zeichen einheitlich zu verwenden und damit die Lesbarkeit des Codes zu verbessern.

Eine einheitliche Verwendung der Schreibweise wird nicht durch den Compiler erzwungen, aber es ist eine gute Gewohnheit, es dennoch zu tun. Eine häufig verwendete Vorgehensweise ist es, nur den ersten Buchstaben jedes Bezeichners groß zu schreiben. Wenn ein Bezeichner aus mehreren aufeinanderfolgenden Wörtern besteht (Sie können keine Leerzeichen in einem Bezeichner verwenden), so sollte jeder erste Buchstabe eines Wortes groß geschrieben werden:

MyLongIdentifier
MyVeryLongAndAlmostStupidIdentifier

Weitere Elemente, die durch den Compiler vollständig ignoriert werden, sind Leerzeichen, Zeilenumbrüche und Tabulatoren, die Sie in den Quellcode einfügen. Alle diese Elemente besitzen die Sammelbezeichnung Trennzeichen (white space). Trennzeichen werden nur zur Verbesserung der Lesbarkeit des Codes verwendet; sie beeinflussen nicht die Übersetzung.

Im Gegensatz zu BASIC gestattet Ihnen Pascal, eine Anweisung über mehrere Code-Zeilen zu schreiben, eine lange Instruktion auf zwei oder mehr Zeilen aufzuteilen. Der Nachteil (zumindest für viele BASIC-Programmierer) dieser Zulässigkeit von Anweisungen auf mehr als einer Zeile besteht darin, dass Sie daran denken müssen, ein Semikolon als Kennzeichen für das Ende der Anweisung anzufügen, oder um genauer zu sein, um eine Anweisung von der nächsten zu trennen. Beachten Sie, dass die einzige Einschränkung bei der Aufteilung von Programmanweisungen über mehrere Zeilen darin besteht, dass sich ein Zeichen-String nicht über mehrere Zeilen erstrecken kann.

Wiederum existieren keine festen Regeln für die Verwendung von Trennzeichen und mehrzeiligen Anweisungen, sondern nur einige Faustregeln:

Code-Einrückung

Der letzte Hinweis über die Verwendung von Trennzeichen steht im Zusammenhang mit dem für die Pascal-Sprache typischen Formatierungsstil, der als Code-Einrückung (pretty-printing) bekannt ist. Die Regel ist einfach: jedes mal, wenn Sie eine zusammengesetzte Anweisung schreiben müssen, so rücken Sie den Rest der nachfolgenden Anweisungen um zwei Leerzeichen ein. Eine zusammengesetzte Anweisung innerhalb einer anderen zusammengesetzten Anweisung ist um vier Zeichen eingerückt usw.:

if ... then
  Anweisung;

if ... then
begin
  Anweisung1;
  Anweisung2;
end;

if ... then
begin
  if ... then
    Anweisung1;
  Anweisung2;
end;

Die obere Formatierung basiert auf der Code-Einrückung, aber Programmierer verwenden unterschiedliche Interpretationen dieser allgemeinen Regel. Einige Programmierer rücken die begin und end-Anweisung zusammen mit dem inneren Code ein, einige von ihnen rücken begin und end ein und rücken danach den inneren Code erneut ein, andere Programmierer setzen das begin auf die Zeile der if-Bedingung. Dies ist hauptsächlich eine Sache des persönlichen Geschmacks.

Ein ähnliches Einrückungsformat wird häufig für Variablenlisten oder Datentypen verwendet und um eine Anweisung der vorherigen Zeile fortzusetzen:

type
  Letters = set of Char;
var
  Name: string;
begin
   { lange Kommentare und lange Anweisungen werden in der 
     folgenden Zeile um zwei Leerzeichen eingerückt }
   MessageDlg ('Dies ist eine Nachricht',
     mtInformation, [mbOk], 0);

Natürlich sind alle diese Konventionen nur ein Vorschlag, um den Code für andere Programmierer besser lesbar zu gestalten, und sie werden durch den Compiler vollständig ignoriert. Ich habe versucht, diese Regeln in allen Beispielen und Code-Fragmenten dieses Buchs einzuhalten. Der Quellcode von Delphi, die Handbücher und Hilfe-Beispiele verwenden einen ähnlichen Formatierungsstil.

Syntaxhervorhebung

Um das Lesen und Schreiben von Pascal-Code zu vereinfachen, besitzt der Delphi-Editor eine Eigenschaft, die als farbliche Syntaxhervorhebung bezeichnet wird. Wenn Sie ein Word in den Editor eingeben, wird es in Abhängigkeit von seiner Bedeutung in Pascal in unterschiedlichen Farben dargestellt. Standardmäßig werden Schlüsselwörter fett dargestellt, Zeichenketten und Kommentare farbig (und teilweise kursiv) usw.

Reservierte Wörter, Kommentare und Zeichenketten sind wahrscheinlich die drei Elemente, die am Stärksten von dieser Eigenschaft profitieren. Sie können auf einen Blick ein falsch geschriebenes Schlüsselwort, eine falsch beendete Zeichenkette oder die Länge eines mehrzeiligen Kommentars erkennen.

Sie können die Syntaxhervorhebung sehr einfach anpassen, indem Sie die Seite Farben des Dialogs Umgebungsoptionen (bzw. Editoreigenschaften in Delphi 5) verwenden (siehe Abbildung 2.1). Wenn Sie nur alleine arbeiten, so können Sie die Farben nach Ihrem Geschmack auswählen. Wenn Sie mit anderen Programmierern eng zusammenarbeiten, so sollten sich alle auf ein gemeinsames Farbschema einigen. Ich empfinde die Arbeit auf einem Computer mit einer anderen Syntaxhervorhebung als der von mir verwendeten als echt schwierig.

Abbildung 2.1: Der Dialog für die Einstellung der farbigen Syntaxhervorhebung

Hinweis: In diesem Buch habe ich mich bemüht, eine Art von Syntaxhervorhebung in den Quelltextbeispielen zu verwenden. Ich hoffe, dass sie dadurch besser lesbar sind.

Die Verwendung von Quelltextvorlagen

Mit Delphi 3 wurde ein neues Merkmal eingeführt, welches mit dem Editieren des Quelltexts zusammenhängt. Wenn Sie Anweisungen in der Sprache Pascal schreiben, so wiederholen Sie die selbe Folge von Schlüsselwörtern. Daher hat Borland ein neues Feature bereitgestellt, welches als Quelltextvorlage (Code Template) bezeichnet wird. Eine Quelltextvorlage ist einfach ein Quelltextabschnitt, der mit einem Kürzel verbunden ist. Sie geben dieses Kürzel ein, drücken anschließend Strg+J und der vollständige Quelltextabschnitt erscheint. Wenn Sie beispielsweise arrayd eingeben und anschließend Strg+J drücken, so wird der Delphi-Editor ihren Text erweitern in:

array [0..] of ;

Da die vordefinierten Quelltextvorlagen gewöhnlich verschiedene Versionen des selben Konstrukts beinhalten, wird das Kürzel allgemein mit einem Buchstaben beendet, der die Version kennzeichnet, an der sie interessiert sind. Sie können jedoch auch nur den Anfang eines Kürzels eingeben. Wenn Sie beispielsweise ar eingeben und dann Strg+J drücken, so wird der Editor ein lokales Menü mit einer Liste der verfügbaren Auswahlmöglichkeiten zusammen mit einer kurzen Beschreibung anzeigen, wie Sie in Abbildung 2.2 sehen können.

Abbildung 2.2: Die Auswahl von Quelltextvorlagen

Sie können die Quelltextvorlagen vollständig anpassen, indem Sie die existierenden Quelltextvorlagen modifizieren oder Ihre eigenen häufig verwendeten Quelltextabschnitte hinzufügen. Denken Sie bitte daran, wenn Sie so etwas tun, dass der Text einer Quelltextvorlage stets das Zeichen '|' enthält, welches anzeigt, wohin der Cursor am Ende der Operation springen soll, d.h. wo Sie die Eingabe beginnen, um die Vorlage mit anwendungsspezifischem Code zu vervollständigen.

Anweisungen der Sprache

Wenn Sie einige Bezeichner definiert haben, so können Sie sie in Anweisungen und in Ausdrücken verwenden, die Teil weiterer Anweisungen sind. Pascal bietet verschiedene Anweisungen und Ausdrücke an. Lassen Sie uns zunächst einen Blick auf Schlüsselwörter, Ausdrücke und Operatoren werfen.

Schlüsselwörter

Schlüsselwörter sind alle die reservierten Bezeichner in Object Pascal, welche eine Rolle in der Sprache spielen. Die Delphi-Hilfe unterscheidet zwischen reservierten Wörtern und Direktiven: reservierte Wörter können nicht als Bezeichner verwendet werden während Direktiven nicht als solche verwendet werden sollten, auch wenn der Compiler diese akzeptieren wird. In der Praxis sollten Sie keine Schlüsselwörter als Bezeichner verwenden.

In Tabelle 2.1 können Sie eine vollständige Liste der Bezeichner sehen, die eine besondere Rolle in der Sprache Object Pascal (in Delphi 4) besitzen, einschließlich der Schlüsselwörter und anderen reservierten Wörtern.

Tabelle 2.1: Schlüsselwörter und andere reservierte Wörter in der Sprache Object Pascal.

Schlüsselwort

Bedeutung

absolute Direktive (Variablen)
abstract Direktive (Methode)
and Operator (Boolean)
array Typ
as Operator (RTTI)
asm Anweisung
assembler Abwärtskompatibilität (asm)
at Anweisung (Exceptions)
automated Sichtbarkeitsattribut (Klasse)
begin Blockkennzeichner
case Anweisung
cdecl Aufrufkonvention bei Funktionen
class Typ
const Deklaration oder Direktive (Parameter)
constructor spezielle Methode
contains Operator (Set)
default Direktive (Eigenschaft)
destructor spezielle Methode
dispid Dispatch-ID für Dispatch-Schnittstellen
dispinterface Typ
div Operator
do Anweisung
downto Anweisung (for)
dynamic Direktive (Methode)
else Anweisung (if oder case)
end Blockkennzeichner
except Anweisung (Exceptions)
export Abwärtskompatibilität (Klasse)
exports Deklaration
external Direktive (Funktionen)
far Abwärtskompatibilität (Klasse)
file Typ
finalization Unit-Struktur
finally Anweisung (Exceptions)
for Anweisung
forward Funktionsdirektive
function Deklaration
goto Anweisung
if Anweisung
implementation Unit-Struktur
implements Direktive (Eigenschaft)
in Operator (set) - Projektstruktur
index Direktive (Dispatch-Schnittstelle)
inherited Anweisung
initialization Unit-Struktur
inline Abwärtskompatibilität (siehe asm)
interface Typ
is Operator (RTTI)
label Deklaration
library Programmstruktur
message Direktive (Methode)
mod Operator (math)
name Direktive (function)
near Abwärtskompatibilität (Klasse)
nil Wert
nodefault Direktive (Eigenschaft)
not Operator (Boolean)
object Abwärtskompatibilität (Klasse)
of Anweisung (case)
on Anweisung (Exceptions)
or Operator (Boolean)
out Direktive (Parameter)
overload Funktionsdirektive
override Funktionsdirektive
package Programmstruktur (Package)
packed Direktive (record)
pascal Aufrufkonvention bei Funktionen
private Sichtbarkeitsattribut (Klasse)
procedure Deklaration
program Programmstruktur
property Deklaration
protected Sichtbarkeitsattribut (Klasse)
public Sichtbarkeitsattribut (Klasse)
published Sichtbarkeitsattribut (Klasse)
raise Anweisung (Exceptions)
read Eigenschaftsvereinbarung
readonly Direktive für Dispatch-Schnittstelle
record Typ
register Aufrufkonvention bei Funktionen
reintroduce Funktionsdirektive
repeat Anweisung
requires Programmstruktur (Package)
resident Direktive (Funktionen)
resourcestring Typ
safecall Aufrufkonvention bei Funktionen
set Typ
shl Operator (mathematisch)
shr Operator (mathematisch)
stdcall Aufrufkonvention bei Funktionen
stored Direktive (Eigenschaft)
string Typ
then Anweisung (if)
threadvar Deklaration
to Anweisung (for)
try Anweisung (Exceptions)
type Deklaration
unit Unit-Struktur
until Anweisung
uses Unit-Struktur
var Deklaration
virtual Direktive (Methode)
while Anweisung
with Anweisung
write Eigenschaftsvereinbarung
writeonly Direktive für Dispatch-Schnittstelle
xor Operator (Boolean)

Ausdrücke und Operatoren

Es existiert keine allgemeine Regel für den Aufbau von Ausdrücken, da sie hauptsächlich von den Operatoren abhängen, die verwendet werden, und Pascal besitzt eine ganze Reihe von Operatoren. Es gibt logische, arithmetische, Boolsche, relationale und Mengenoperatoren sowie einige weitere. Ausdrücke können verwendet werden, um einen Wert zu ermitteln, der einer Variable zugewiesen werden soll, einen Parameter einer Funktion oder Prozedur zu berechnen oder um eine Bedingung zu prüfen. Ausdrücke können auch Funktionsaufrufe beinhalten. Jedes mal, wenn Sie eine Operation auf einen Wert oder einen Bezeichner anwenden, anstatt den Bezeichner selbst zu verwenden, handelt es sich um einen Ausdruck.

Ausdrücke sind in den meisten Programmiersprachen üblich. Ein Ausdruck ist eine gültige Kombination aus Konstanten, Variablen, literalen Werten, Operatoren und Funktionsergebnissen. Ausdrücke können auch an Wertparameter von Prozeduren und Funktionen übergeben werden, aber nicht immer an Referenzparameter (welche einen zuweisbaren Wert erfordern).

Operatoren und ihre Rangfolge

Wenn Sie schon jemals in Ihrem Leben ein Programm geschrieben haben, so wissen Sie bereits was ein Ausdruck ist. An dieser Stelle möchte ich die besonderen Elemente von Pascal-Operatoren beleuchten. Sie können eine Liste aller Operatoren der Sprache, gruppiert nach ihrer Rangfolge, in Tabelle 2.1 sehen.

Hinweis: Im Gegensatz zu den meisten anderen Programmierprachen haben die Operatoren and und or eine höhere Rangfolge als die relationalen Operatoren. Wenn Sie also schreiben a < b and c < d, so wird der Compiler versuchen, die Und-Operation zuerst auszuführen, was zu einem Übersetzungsfehler führt. Aus diesem Grund sollten Sie jeden der < Ausdrücke in Klammern setzen: (a < b) and (c < d).

Einige der bekannten Operatoren besitzen eine unterschiedliche Bedeutung bei unterschiedlichen Datentypen. Beispielsweise kann der + Operator verwendet werden, um zwei Zahlen zu addieren, zwei Strings zu verketten, die Vereinigungsmenge aus zwei Mengen zu bilden und sogar einen Wert zum Offset auf einen PChar-Zeiger zu addieren. Sie können jedoch nicht zwei Zeichen addieren, wie es in C möglich ist.

Ein weiterer seltsamer Operator ist div. In Pascal können Sie zwei beliebige Zahlen (reelle oder ganze Zahlen) mit dem / Operator dividieren. Sie werden stets ein reelles Ergebnis erhalten. Wenn Sie zwei ganzzahlige Werte dividieren möchten und das ganzzahlige Ergebnis benötigen, so verwenden Sie statt dessen den Operator div.

Tabelle 2.2: Operatoren in der Sprache Pascal, geordnet nach ihrer Rangfolge

Unäre Operatoren (höchste Rangfolge)

@ Adresse von einer Variablen oder Funktion (liefert einen Zeiger zurück)
not Boolesche oder bitweise Negation

Multiplikative und bitweise Operatoren

* Arithmetische Multiplikation oder Schnittmenge
/ Gleitkommadivision
div Integer-Division (ganzzahlig)
mod Modulo (der Rest einer Integer-Division)
as Typsichere Typumwandlung (RTTI)
and Boolesche oder bitweise Und-Verknüpfung
shl bitweise Linksverschiebung
shr bitweise Rechtsverschiebung

Additive Operatoren

+ Arithmetische Addition, Vereinigungsmenge, String-Verkettung, Addition eines Zeiger-Offsets
- Arithmetische Subtraktion, Differenzmenge, Subtraktion eines Zeiger-Offsets
or Boolesche oder bitweise Oder-Verknüpfung
xor Boolesche oder bitweise Exklusiv-Oder-Verknüpfung

Relationale und Vergleichsoperatoren (niedrigste Rangfolge)

= Test auf Gleichheit
<> Test auf Ungleichheit
< Test auf kleiner als
> Test auf größer als
<= Test auf kleiner als oder Gleichheit, oder eine Teilmenge von einer Menge
>= Test auf größer als oder Gleichheit, oder eine Obermenge von einer Menge
in Test ob ein Wert Element einer Menge ist
is Test ob ein Objekt typkompatibel ist (ein weiterer RTTI Operator)

Mengenoperatoren

Die Mengenoperatoren beinhalten die Vereinigung (+), die Differenz (-), die Schnittmenge (*), die Prüfung auf Mitgliedschaft eines Elements (in) sowie zusätzlich einige relationale Operatoren. Um ein Element zu einer Menge hinzuzufügen, können Sie eine Vereinigung einer Menge mit einer weiteren Menge durchführen, die nur das benötige Element enthält. Hier ist ein Delphi-Beispiel das sich auf den Schriftartstil bezieht:

Style := Style + [fsBold];
Style := Style + [fsBold, fsItalic] - [fsUnderline];

Als eine Alternative können Sie die Standardprozeduren Include und Exclude verwenden, welche deutlich effizienter sind (aber nicht mit Komponenteneigenschaften vom Typ Menge verwendet werden können, da sie einen Referenzparameter erwarten).

Include (Style, fsBold);

Zusammenfassung

Nun, wo wir das grundsätzliche Aussehen eines Pascal-Programms kennengelernt haben, sind wir bereit, seine Bedeutung in Detail zu verstehen. Wir werden damit beginnen, die Definition von vordefinierten und anwenderdefinierten Datentypen zu untersuchen. Anschließend gehen wir auf die Verwendung von Schlüsselwörtern zur Bildung von Programmanweisungen ein.

Nächstes Kapitel: Typen, Variablen und Konstanten

© Copyright Marco Cantù, Wintech Italia Srl 1995-2000
© Copyright der deutschen Übersetzung Immo Wache, 2000