Höhere Sprachebene erleichtert das Strukturieren von Programmen, aber:

Konfuse Konstrukte lassen sich kaum ausmerzen

19.09.1986

Höhere Programmiersprachen machen die Strukturierung von Programmen leichter. Eine Garantie dafür, daß die Programmierer nicht dennoch ziemlich konfuse Konstrukte in ihren Code einbauen, bieten die traditionellen Sprachen jedoch keineswegs. Einen Überblick über die Entwicklung in diesem Bereich gibt Horst Burwick*.

Eine allgemeine Software-Krise hat es in der Realität wohl nie gegeben, denn das Wesentliche einer Krise liegt darin, daß sie nur einen relativ kurzen Zeitraum anhält, in dem sie entweder bewältigt wird oder an dessen Ende die Katastrophe steht. Tatsache ist vielmehr, daß wir uns nunmehr über zwei Jahrzehnte hinweg in einem Zustand befinden, der höchst unbefriedigend ist und der sich in der allgemeinen Unzufriedenheit der Fachabteilungen über die Qualität und Quantität der Leistungen der zentralen DV-Abteilungen äußert.

Wie aber soll sich dieser Zustand jemals ändern? Die Antwort auf diese Frage lautet: durch den Einsatz höherer Sprachen. Wir müssen wegkommen von den traditionellen Sprachen der kommerziellen Datenverarbeitung, Cobol und PL/ 1, und vor allem auch die damit induzierten Denkweisen und Projektschemata überwinden.

In einem DV-Projekt geht es immer darum, drei Qualitätskriterien zu erfüllen. An erster Stelle steht die Korrektheit des Systems. Das heißt, es muß insgesamt seiner Zielsetzung gerecht werden, und die Programme müssen die einzelnen Berechnungen und Auswertungen richtig durchführen. Die beiden nachfolgenden Kriterien sind die Wartbarkeit und die effiziente Nutzung gegebener Hardware-Ressourcen. Eine wohldefinierte und gut implementierte höhere Programmiersprache hilft dabei, jedes einzelne dieser Kriterien zu erfüllen.

Am leichtesten akzeptiert die Fachwelt diese Aussage bezüglich der Wartbarkeit. Vergleicht man etwa ein Cobol-Programm mit einem Assembler-Programm, so erkennt man, daß der Cobol-Code besser strukturiert ist, und damit sind die zu ändernden Stellen leichter zu lokalisieren und einfacher zu ändern, also sind solche Programme besser zu warten. Ebenso sind kürzere und besser strukturierte Programme leichter 2U verstehen und zu testen. Sie sind also mit größerer Wahrscheinlichkeit korrekt.

Höhere Programmiersprachen machen die Strukturierung von Programmen leichter. Aber die Garantie dafür, daß die Programmierer nicht doch ziemlich konfuse Konstrukte in ihre Programme einbauen, bieten die traditionellen Sprachen keineswegs.

Unglaublich scheint für die meisten, daß die Verwendung höherer Sprachen auch zu effizienteren Programmen führen soll. Um dieses zu verstehen, muß man sich klarmachen, daß nicht nur die Sprache, sondern vor allem auch der Anwendungsprogrammierer einen entscheidenden Einfluß auf die Laufzeiten eines Programms hat.

Es ist klar, daß die niedrigere Sprache wegen der höheren Freiheitsgrade bei der Realisierung eines Programms theoretisch die Entwicklung schnellerer Programme gestattet. Mit zunehmender Komplexität der Aufgabe klafft aber eine sehr ernst zu nehmende Lücke zwischen dem theoretischen Optimum und dem in der Praxis erreichbaren Wert. Und diese Lücke ist um so größer, je niedriger die Programmiersprache ist. Wenn also die zu programmierende Aufgabe genügend komplex ist, kann man ziemlich sicher sein, daß ein guter PL/ 1-Programmierer hierzu ein Programm schreibt, welches weniger Zeit- und Platz-Ressourcen verbraucht als ein gleichermaßen qualifizierter Assembler-Programmierer.

Assembler-Einsatz ist unwirtschaftlich

Hinzu kommt der Aspekt, daß sich Programme in der höheren Sprache mit weniger Aufwand und in kürzerer Zeit entwickeln lassen und daß die Performance der Programme kaum noch durch eigene Anweisungen, sondern durch das verwendete Datenbanksystem und Terminalsystem bestimmt wird. Deshalb erscheint es ziemlich unwirtschaftlich, heute noch im Organisationsbereich Assembler als Programmiersprache einzusetzen. Dies sollte allgemein bekannt sein. Dennoch gibt es in der Tat noch mehr Unternehmen als man glaubt, die auf diesem Entwicklungsniveau stehen.

Bei der Einführung von 4th Generation Languages sind fast die gleichen organisatorischen und menschlichen Probleme zu überwinden, wie sie vor Jahren bei den meisten Unternehmen aufgetreten sind, die mit Cobol oder PL/1 die Assembler-Programmierung abgelöst haben. Denn bei jedem Übergang zu einem höheren Programmierniveau geschieht das gleiche: Man erhält einen höheren Service zur Erstellung von Programmen und muß dafür bezahlen mit einer Verminderung des Einflusses, den man auf die Implementierung eines Programms nehmen kann.

Die von Marketingexperten eingeführte Bezeichnung "4th Generation Languages" ist sehr irreführend. Im Hardware-Bereich spricht man von einer neuen Generation, wenn eine alle Technologie durch eine neue abgelöst wird. Über kurz oder lang werden dann alle neuen Computer in der neuen Technologie gebaut. Die veraltete Technologie stirbt aus. Es gibt eine neue Generation von Rechnern.

Diese Linearität der Entwicklung, bei der eine beherrschende Technologie durch eine neue abgelöst wird, hat es im Software-Bereich nie gegeben. Am ähnlichsten ist allenfalls noch die Situation bei den Betriebssystemen. Für Programmiersprachen ist eine Einteilung in Generationen weder hilfreich noch sinnvoll und im Grunde genommen sogar falsch.

Besser ist es, von Sprachebenen zu sprechen und diese genauer zu definieren. Dabei sollte es nicht verwundern, wenn die älteren Programmiersprachen vorwiegend in den unteren Ebenen, die neueren eher in den oberen anzutreffen sind. Dennoch lassen sich jüngere Sprachen wie Pascal, Ada und C einer niedrigeren Ebene zuweisen als die älteren Sprachen Lisp und APL. Die Zuordnung zu einer Ebene ist kein Qualitätskriterium.

Fünf Ebenen sind zu unterscheiden

Die Sprachen werden entsprechend dem Service, den sie bieten, den Ebenen zugeteilt, nach der Regel: Wenig Service ergibt eine niedrigere Sprachebene, viel Service eine höhere. Für die Durchführung einer Klassifizierung der Programmiersprachen ist diese Regel kaum praktikabel. Wird jedoch als Maß angesetzt, was in den Programmiersprachen noch als Hardware-Information übrigbleibt, so kommt man schnell zu einer Einteilung, die sich vorwiegend an dem orientiert, was von der Rechnerarchitektur, insbesondere vom Aufbau der Speicher, noch in den Programmiersprachen bekannt ist. Somit unterscheiden sich fünf Ebenen:

- interner Code,

- Assembler,

- problemorientierte Sprachen,

- datenorientierte Sprachen,

- wissensorientierte Sprachen.

Der Intern-Code fordert eine ausschließlich numerische Codierung der Programme, die das Gedächtnis stark belastet. Jede Änderung im Code erfordert eine völlige Neuberechnung der Adressen, wenn man keine "Rucksäcke" programmieren will, das heißt einen Sprung ans Ende des Programms und zurück zur aufrufenden Stelle. Der Service, den der Computer beim Programmieren gibt, ist gleich null.

Externe Speicher werden als Dateien aufgefaßt

Die Assembler-Sprachen brachten einen allgemein rasch akzeptierten Service, Mnemo-Codes und symbolische Adressen. Dieser Service ist nicht einmal durch die Aufgabe irgendeines Einflusses zu bezahlen.

Die verbleibenden Probleme, geregnete Registerverwendungen und Speicheraufteilungen zu finden und auch der Wunsch, mathematischtechnische Algorithmen in gewohnter Terminologie zu formulieren, führten dann 1954 J.F. Backus dazu, Fortran, die erste Sprache der dritten Sprachebene, zu definieren. Vier Jahre darauf folgte Algol, 1959 Cobol, 1964 PL/1, aber auch Basic und später Pascal, Ada und "C", um nur die wichtigsten aufzuzählen.

So unterschiedlich diese Sprachen auch sein mögen, in einem Punkt sind sie alle gleich: Sie zeigen dem Programmierer nicht mehr, daß ein Computer Register hat. Selbstverständlich lassen sie auch nicht mehr die Maschineninstruktionen erkennen. Auf verschiedenen Maschinen sind die gleichen Sprachen verfügbar. Die Anwendungsprogramme wurden zunehmend portabel. Trotzten ist es manchmal nicht leicht, Fortran-, Cobol- oder PL/ 1 -Programme auf einen anderen Rechner zu übertragen.

Aber nicht nur in dem, was sie vor konkreten Rechnern verbergen, gleichen sich die zitierten Sprachen, sondern auch in dem, was sie deutlich sichtbar von der Rechnerarchitektur ausweisen: nämlich, daß es einen Hauptspeicher und externe Speicher gibt. Die Verbindung dieser beiden Bereiche wird durch Lese- und Schreibbefehle bewältigt, die einzelne Sätze hin- und hertransportieren. Externe Speicher werden als Dateien aufgefaßt, die aus Sätzen bestehen. Man orientiert sich einfach an dem Datenbild, das von dem Betriebssystem geliefert wird.

Diese Betrachtung aller externen Datenbestände rührt daher, daß die ersten Vertreter dieser Sprachebene - Fortran, Algol, Cobol und PL/ 1- zu einer Zeit entstanden sind, als man an Datenbanken noch nicht im Traum dachte. Natürlich gab es zu dieser Zeit auch noch keine Bildschirme und damit weder die Online-Entwicklung noch das Programmieren von Transaktionen. Das folgte alles etwas später und zusätzlich stiegen auch noch die Ansprüche der Anwender.

Damit verloren die traditionellen Sprachen eine wesentliche Eigenschaft, den Anspruch der Vollständigkeit. Mit ihnen alleine lassen sich heute geforderte Programme nicht mehr entwickeln. Die Sprachen enthalten Löcher, die gestopft werden müssen. Die traditionellen Sprachen dienen deshalb Datenbank- und Terminalsystemen als Host-Languages, die durch Generatoren ergänzt werden. Das Aufgabenfeld beinhaltet beispielsweise normierte Programmierung, Entscheidungstabellen oder Bildschirmmasken.

Neue Sprachen begeistern die Programmierer nicht

Man sollte annehmen, daß die Vielfalt der Systeme, die in ihren Syntaxschemata in keiner Weise zueinander passen, zu einer Frustration der Programmierer führt. Genau das Gegenteil scheint jedoch der Fall zu sein: Neue Sprachen, die diese veränderten Anforderungen wieder auf einen einheitlichen konzeptionellen Nenner bringen, begeistern die Programmierer nicht, zumal die Vereinfachungen sogar so weit gehen, daß exklusives Wissen über technische Details überhaupt nicht mehr erforderlich ist.

Dies ist ein wesentlicher Teil der großen Akzeptanz-Problematik, denen die Sprachen der nächsten Ebene begegnen - Sprachen, die sehr viel jugendliche Unbekümmertheit aufweisen. Deshalb kann man es vielleicht durchgehen lassen, sie voller Begeisterung einer neuen Generation zuzurechnen, den 4 GLs.

Um aber die Systematik der fünf Sprachschichten nicht ganz aus den Augen zu verlieren, ist von diesen Sprachen zu fordern, daß sie nach den Registern nun auch den Hauptspeicher aus unseren Überlegungen verschwinden lassen. Sie sollten ferner mit einem logischen Datenmodell aufwarten, zu dem es anspruchsvollere Operationen gibt als nur das Lesen und Schreiben von einzelnen Sätzen .

Forscher bevorzugen die fünfte Generation

Zu untersuchen, inwieweit die auf dem Markt von Hardwareherstellern und Softwarehäusern unter dem Markenzeichen 4 GLs angebotenen Systeme wie Mapper, AS, Natural Mantis, Gogol, Infplan, Merkur, EPS, Matplan, Ufo, Focus und viele andere dieses Kriterium erfüllen, wäre viel: eicht einmal eine interessante Aufgabe für eine Hochschule.

Bemerkenswert ist, daß in den einschlägigen Publikationen der Informatik diese Sprachen überhaupt nicht behandelt werden. Die Wissenschaft wendet sich lieber der nächsten Schicht von Sprachen zu, in denen dann weder Daten noch Speicherstrukturen zu erkennen sind: den Sprachen der fünften Generation, wie etwa Prolog, in denen es um die Darstellung und Verarbeitung von Wissen geht. In den USA beginnen Expertensysteme in den verschiedenartigsten Situationen, die eine Diagnose erfordern, eine Rolle zu spielen. Hierzulande ist man gegenüber der Künstlichen Intelligenz eher noch etwas skeptisch.

*Horst Burwick ist Geschäftsführer der Gesellschaft für Mathematik und Informatik (GMI) in Aachen.