Fortran: Fortran 95: Datenverbund
<<< zur Fortran-Startseite | |
<< Fortran 95 | Fortran 2003 >> |
< Datentypen höherer Genauigkeit | Standardfunktionen > |
Einleitung
BearbeitenDatenelemente lassen sich auch zu eigenen zusammengesetzten Datentypen verbinden. Der Datenverbund ist in anderen Programmiersprachen auch als Struktur (structure, struct) bekannt. Der Fortran 95-Standard spricht vom "derived type", also einem abgeleiteten Datentyp. Zulässig als Komponenten eines Datenverbundes sind Skalare, Felder, Zeiger oder auch andere Datenverbunde. Ein Datenverbund ist durch das Schlüsselwort type
gekennzeichnet und kann in folgenden Formen auftreten
|
|
Die Elemente in eckigen Klammern sind optional. Die Angabe eines Zugriffsspezifizierers (public
, private
) ist nur bei Verwendung von Datenverbunden in Modulen erlaubt.
Einen Datenverbund anlegen
Bearbeitentype :: name [sequence] ! optional sequentielle Speicherplatzablage datentyp :: komponentenname_1 ! ... datentyp :: komponentenname_n end type [name] |
Beispiel (Programmausschnitt):
Fortran 90/95-Code (free source form) |
! ... type :: koord integer :: id real, dimension(3) :: x end type koord ! ... |
Eine Variable vom Typ "Datenverbund" anlegen
BearbeitenDie Variablendeklaration erfolgt in der Form
type( name ) :: var |
Beispiel (Programmausschnitt):
Fortran 90/95-Code (free source form) |
! ... type :: koord integer :: id real, dimension(3) :: x end type koord type( koord ) :: k ! ... |
Zugriff auf Einzelkomponenten eines Datenverbunds
BearbeitenEine Einzelkomponente in einem Datenverbund lässt sich als Kombination des Datenverbundvariablenbezeichners und des Komponentennamen ansprechen. Verknüpft werden diese beiden Bezeichner mit dem %
-Zeichen.
var%komponentenname |
Beispiel (Programmausschnitt):
Fortran 90/95-Code (free source form) |
! ... type :: koord integer :: id real, dimension(3) :: x end type koord type( koord ) :: k k%id = 999 k%x(1) = 0.0 k%x(2) = 20.5 k%x(3) = 10.0 write( *, * ) k%x(2) ! ... |
Zugriff auf einen Datenverbund als Ganzes
BearbeitenEin Datenverbund kann in bestimmten Situation nicht nur komponentenweise angesprochen werden, sondern auch als Einheit, z.B. bei der Ein-/Ausgabe oder beim Zuweisen der Werte einer Datenverbundvariablen an eine andere.
Beispiel (Programmausschnitt):
Fortran 90/95-Code (free source form) |
! ... type :: koord integer :: id real, dimension(3) :: x end type koord type( koord ) :: k1, k2 read( *, * ) k1 k2 = k1 write( *, * ) k2 ! ... |
Elemente eines Datenverbunds initialisieren
BearbeitenDefault-Werte im Datenverbund setzen
BearbeitenInnerhalb eines Datenverbundes lassen sich die einzelnen Variablen mit Vorgabewerten belegen, z.B.
integer :: i = 5 character, dimension( 2, 2 ) :: c = reshape( (/ "A", "B", "C", "D" /), (/ 2, 2 /) )
Beispiel:
Fortran 90/95-Code (free source form) |
program bsp implicit none type :: koord integer :: id = -999999 real, dimension( 3 ) :: x = 0.0 end type koord type( koord ) :: k write( *, * ) k ! Ausgabe: ! -999999 0.0 0.0 0.0 end program bsp |
Der "structure constructor"
BearbeitenDie Initialisierung der Datenverbundelemente bzw. eine spätere Wertzuweisung kann auch per "structure constructor" ("derived type value constructor") vorgenommen werden.
name( wertliste ) |
Beispiel:
Fortran 90/95-Code (free source form) |
program bsp implicit none type :: koord integer :: id real, dimension( 3 ) :: x end type koord type( koord ) :: k = koord( 12, (/ 0.0, 1.5, 20.5 /) ) write( *, * ) k k = koord( 13, (/ 5.5, 0.0, 0.5 /) ) write( *, * ) k ! Ausgabe: ! 12 0.0 1.5 20.5 ! 13 5.5 0.0 0.5 end program bsp |
Enthält ein Datenverbund bereits Variablen mit Vorgabewerten, so werden diese durch die Werte im "structure constructor" überschrieben.
Beispiel:
Fortran 90/95-Code (free source form) |
program bsp implicit none type :: person character(25) :: vorname = 'NN' character(25) :: nachname = 'NN' integer :: alter end type person type(person), dimension(5) :: p p(1) = person('Harri', 'P.', 41) p(5) = person('Creszenzia', 'T.', 18) write(*, fmt=111) p ! Ausgabe: ! Harri P. 41 ! NN NN 0 ! NN NN 0 ! NN NN 0 ! Creszenzia T. 18 write(*,*) p(1)%vorname ! Ausgabe: ! Harri p(2)%vorname = 'Holger' write(*, '(A)') p%vorname ! Ausgabe: ! Harri ! Holger ! NN ! NN ! Creszenzia 111 format(2A, I3) end program bsp |
Beispiel: Verwendung eines Datenverbunds in einem anderen Datenverbund
Fortran 90/95-Code (free source form) |
program bsp implicit none type :: tripel real :: x, y, z end type tripel type :: koerper integer :: id type( tripel ) :: bezugskoordinate type( tripel ) :: orientierung end type koerper type( koerper ) :: k k = koerper( 1005, tripel( 10.5, 0.0, -6.5 ), tripel( 0.0, 0.0, -0.8 ) ) write( *, * ) k ! Ausgabe: ! 1005 10.50000 0.000000 -6.500000 0.000000 ! 0.000000 -0.8000000 end program bsp |
Das Attribut sequence
Bearbeiten
Im Datenverbund kann zu Beginn auch das Attribut sequence
angegeben werden. Dieses spezifiziert, dass die Werte eines Datenverbunds sequentiell gespeichert werden. Wird dieses Attribut weggelassen, so ist nicht gewährleistet, dass die Werte von Datenverbundvariablen in der selben Reihenfolge, wie sie im Datenverbund gereiht wurden im Speicher wiederzufinden sind, oder dass sie zusammenhängend gespeichert werden. Oft wird die Speicherreihenfolge keine wesentliche Rolle spielen. Ein Spezialfall, wo die Speicherreihenfolge jedoch essenziell ist, wird anschließend dargestellt.
Die Verwendung eines Datenverbunds in separaten Programmeinheiten
BearbeitenEin Datenverbund kann über ein Modul verschiedenen Programmeinheiten bekannt gemacht werden. Dazu aber später. Es ist nämlich auch so möglich in komplett getrennten Programmeinheiten auf ein und denselben Datenverbund-Datentyp zuzugreifen.
Beispiel: Ein ähnliches Beispiel findet sich auch im J3/97-007R2 Working Draft, Note 4.31
Fortran 90/95-Code (free source form) |
program bsp implicit none type :: koord sequence integer :: id real, dimension( 3 ) :: x end type koord type( koord ) :: k = koord( 555, (/ 3.0, 4.0, 5.5 /) ) call ausgabe( k ) ! Ausgabe ! 555 3.0000000 4.0000000 5.5000000 end program bsp subroutine ausgabe( coord ) type :: koord sequence integer :: id real, dimension( 3 ) :: x end type koord type( koord ), intent( in ) :: coord write( *, * ) coord end subroutine ausgabe |
In diesem speziellen Fall muss der Datenverbund lt. Standard mit dem Attribut sequence
versehen werden. Des Weiteren muss der im Hauptprogramm deklarierte Datenverbund komplett identisch mit jenem im Unterprogramm sein (Datenverbundname, Variablenbezeichner, Reihenfolge, Datentypen). In der Praxis sehen das viele Compiler nicht so eng. Allerdings können bei Nichtbeachtung dieser Vorgaben spätestens beim Wechsel des Compilers oder auf andere Rechnerarchitekturen gröbere Probleme auftreten.
<<< zur Fortran-Startseite | |
<< Fortran 95 | Fortran 2003 >> |
< Datentypen höherer Genauigkeit | Standardfunktionen > |