Dies ist eine alte Version des Dokuments!


Schleifen

Schleifen (Iterationen) werden dazu verwendet Quellcode mehrfach hintereinander auszuführen. Abhängig von einer Bedingung kann Code also wiederholt werden.

Klassisches Fortran

In klassichem Fortran wird gibt es eine Zählschleife:

      DO <m> k = <kvon>, <kbis> [, <kstep>]
c       Anweisungscode
<m>   CONTINUE ! oder andere Anweisung

Das ist eine gewöhnliche Zählschleife, die mit k von <kvon> bis <kbis> iteriert, und zwar mit der Schrittgröße <kstep>. Für frühes Fortran galt, dass kstep immer größer als Null sein muss, in Fortran 77 war dann möglich auch negative Zahlen als Schrittgröße zu verwenden.

<m> ist eine Sprungmarkierung. Dorthin wird gesprungen, wenn die Bedingung nicht mehr erfüllt ist. Wichtig ist auch, dass die Anweisung bei der Sprungmarke ebenfalls im Schleifenkörper ausgeführt wird! Ein CONTINUE also als erste Anweisung zu schreiben hat zur Folge, dass an dieser Stelle keine Aktion ausgeführt wird.

In Fortran 77 war es eine Zeit lang möglich auch reelle Zahlen als Zählvariablen (und Schrittgröße) zu wählen. Allerdings entstanden dadurch Probleme, da die Anzahl der Durchläufe nicht immer korrekt bestimmt werden konnte, weil mit reellen Zahlen Rundungsfehler passieren (siehe 0.1 in Binärdarstellung). Heutzutage sollte der Compiler dieses Feature nicht mehr erlauben.

Do-While (Fortran 90)

In Fortran 90 gibt es die Do-While-Schleife, die ähnlich wie While-Schleifen anderer Programmiersprachen aussieht. Dieses Feature wurde oftmals bereits in Fortran 77-Compiler eingebaut.

      DO WHILE (<logischer Ausdruck>)
c       Anweisungscode
      END DO

Im Anweisungscode steht idealerweise Code, der Auswirkung auf den logischen Ausdruck hat. Es ist aber auch möglich aus der Schleife mittels goto herauszuspringen.

Unendliche Schleifen

Passend dazu gibt es noch die unendliche Schleife, die gänzlich ohne Abbruchbedingung auskommt. Idealerweise gibt es im Anweisungsblock allerdings die Möglichkeit aus der Schleife auszubrechen - eine tatsächlich unendliche Schleife ist selten in Programmen nützlich.

      DO
c       code
        IF (<logischer Ausdruck>) EXIT
c       noch mehr code
      END DO

Die Schleife beginnt mit DO, dann folgt der Anweisungsblock (auf der nächsten Zeile). Im Anweisungsblock sollte mit einer Bedingung der Ausbruch aus der Schleife (EXIT) möglich sein.

Steueranweisungen

In Fortran kann mittels spezieller Steueranweisungen bspw. aus einer Schleife ausgebrochen werden (vgl. break / continue aus C):

  • CYCLE → überspringt den Rest der inneren Schleife und führt die innere Schleife erneut aus (vgl. continue)
  • EXIT → bricht aus der aktuellen Schleife aus (vgl. break)

Bsp:

      outer: do i=1,n ! Zählschleife von 1 bis n, Schrittweite 1
c       Anweisungen
        inner: do j=i,n ! Zählschleife von i bis n
c         ...
          if (...) EXIT outer ! verlasse die gesamte Schleife
          if (...) EXIT       ! verlasse nur die innere Schleife
          if (...) CYCLE      ! überspringe den Rest der inneren Schleife
c         ...
        END DO inner
      END DO outer

Hier stehen zwei verschachtelte Zählschleifen von 1 bis n, bzw. von i bis n. Im Inneren sehen Sie verschiedene Steueranweisungen. Mit EXIT outer wird das gesamte Konstrukt verlassen (also die äußere Schleife wird verlassen), mit EXIT wird nur die aktuelle Stufe verlassen (inner) und mit CYCLE wird, ähnlich wie continue in C, der Rest der Schleife übersprungen und sofort mit den nächsten Schleifenelement fortgefahren.

Matrizen ausgeben

:!: Vorgriff auf Kapitel Felder

Die Anweisung write gibt immer eine Zeile aus, dh. egal, was Sie damit ausgeben, am Ende steht immer implizit ein '\n', also ein Zeilenendzeichen. Wollen Sie aber eine Matrix ausgeben, kann es notwendig sein mehrere Werte nebeneinander auszugeben, aber vielleicht wissen Sie nicht wie viele Zahlen das sind. Dafür gibt es folgendes Konstrukt:

      REAL A(1000,1000) ! Array mit 1000x1000 Real-Einträgen
 
      WRITE (*,*) (A(1,j), j=1,m)

Diese Anweisung die die erste Zeile der Matrix aus, dh. der Index j wird von 1 bis m iteriert und die Werte der Matrix an die Stelle des Konstrukts getragen, sodass write alle Werte der Zeile ausgibt. Das Ganze geht auch geschachtelt (dann stehen alle Werte auf einer Zeile):

      REAL A(1000,1000) ! Array mit 1000x1000 Real-Einträgen
 
      WRITE (*,*) ((A(i,j), j=1,m), i=1,n)