Skip to content
GitLab
Explore
Sign in
Primary navigation
Search or go to…
Project
P
PROG-material-public
Manage
Activity
Members
Labels
Plan
Issues
Issue boards
Milestones
Wiki
Code
Merge requests
Repository
Branches
Commits
Tags
Repository graph
Compare revisions
Build
Pipelines
Jobs
Pipeline schedules
Artifacts
Deploy
Releases
Container registry
Model registry
Operate
Environments
Monitor
Incidents
Analyze
Value stream analytics
Contributor analytics
CI/CD analytics
Repository analytics
Model experiments
Help
Help
Support
GitLab documentation
Compare GitLab plans
Community forum
Contribute to GitLab
Provide feedback
Keyboard shortcuts
?
Snippets
Groups
Projects
Show more breadcrumbs
Walter, Wolfgang
PROG-material-public
Commits
d2cef6c7
Commit
d2cef6c7
authored
7 years ago
by
Tony Zorman
Browse files
Options
Downloads
Patches
Plain Diff
added einfuehrung_sub_fun
parent
2ad5c0bb
Branches
Branches containing commit
No related tags found
No related merge requests found
Changes
1
Hide whitespace changes
Inline
Side-by-side
Showing
1 changed file
einfuehrung_sub_fun
+140
-0
140 additions, 0 deletions
einfuehrung_sub_fun
with
140 additions
and
0 deletions
einfuehrung_sub_fun
0 → 100644
+
140
−
0
View file @
d2cef6c7
„in Blatt 4 werden Module, Funktionen und Subroutinen genutzt
Subroutinen: Programmteile, die man wiederverwenden kann
Vorteil: Sachen nicht mehrmals schreiben (Code-Dopplung vermeiden!)
mehr Übersicht, wenn man ignoriert, wie das im Detail passiert und das Hauptprogramm übersichtlich wird
Syntax:“
PROGRAM testprog
! Hauptprogramm
CONTAINS
SUBROUTINE ausgabe(myname)
CHARACTER(len = 5), INTENT(IN) :: myname ! INTENT(IN): ist input, kann nicht verändert werden
WRITE(*,*) "Hallo, mein Name ist ", myname, ". Bitte sprich mit mir."
READ(*,*) ! unnuetze Eingabe
END SUBROUTINE
END PROGRAM
„Dann im HP aufrufen:“
ergänze im obigen Programm:
PROGRAM testprog
IMPLICIT NONE
CALL ausgabe("Dummy")
CONTAINS
...
END PROGRAM
„oft: Eingabe mit Überprüfung auf Sinnhaftigkeit
Nach Ausführung des Unterprogramms soll berechneter (eingegebener) Wert im Hauptprogramm genutzt werden.
Option 1 mit subroutine:“
PROGRAM
SUBROUTINE namenseingabe(eingabeaufforderung, benutzereingabe)
CHARACTER(len = *), INTENT(IN) :: eingabeaufforderung ! len = * -> übernommene Länge
INTEGER, INTENT(OUT) :: benutzereingabe ! voriger Wert des Arguments wird ignoriert
DO
WRITE(*,*) eingabeaufforderung
READ (*,*) benutzereingabe
IF (benutzereingabe > 0) THEN
EXIT
ELSE
WRITE(*,*) "Eingabe fehlerhaft. Bitte nochmal."
END IF
END DO
END SUBROUTINE
„also: Variable außen wird verändert, wenn sie innen neu gesetzt wird
-> darauf immer aufpassen, kann mit INTENT(IN/OUT/INOUT) gut geprüft werden
Alternative: FUNCTION: "wie in der Mathematik" (aber nur, wenn INTENT(IN) angegeben ist,
andernfalls koennen die Eingabeparameter veraendert werden!):
man gibt Argumente rein, bekommt Ergebnis raus
damit kann man weiterrechnen, z.B. mittelwert = REAL(summe)/n (in Zyklus Programm)
Das Ergebnis nennt man "Rückgabewert"“
FUNCTION namenseingabe(eingabeaufforderung)
CHARACTER(len = *), INTENT(IN) :: eingabeaufforderung ! len = * -> übernommene Länge
INTEGER :: namenseingabe ! innerhalb der Funktion ist eingabe eine
! normal nutzbare Variable, bekommt einen Typ
DO
WRITE(*,*) eingabeaufforderung
READ (*,*) namenseingabe
IF (namenseingabe > 0) THEN
EXIT
ELSE
WRITE(*,*) "Eingabe fehlerhaft. Bitte nochmal."
END IF
END DO
END FUNCTION
„um rekursive Funktionen zu schreiben, muss "namenseingabe" als Funktion zur Verfügung stehen.
Dafür muss die Variable, die den Rückgabewert enthält anders heißen:”
RECURSIVE FUNCTION add(a, n) RESULT(sum)
! returns a + n in convoluted method
INTEGER :: a, n, sum
IF (n == 0) THEN
sum = a
ELSE (n < 0) THEN
sum = add(a - 1, n + 1) ! rekursiver Aufruf, liefert (a - 1) + (n + 1)
ELSE
sum = add(a + 1, n - 1) ! auch rekursiver Aufruf
END IF
END FUNCTION
„RESULT kann man immer benutzen, wenn man den Funktionsnamen nicht als Variable in der Funktion nutzen möchte
Um dem Projekt mehr Struktur zu geben, sammelt man Subroutinen, Funktionen, Konstantendeklarationen
in sogenannten Modulen.
Module sind unabhängig von Programmen und können in verschiedenen Programmen wiederverwendet werden.
Z.B. werden wir ein Modul von Prof. Walter für Intervallarithmetik in Kürze sehen”
MODULE simpleIO
IMPLICIT NONE
INTEGER, PARAMETER :: realkind = SELECTED_REAL_KIND(p = 15, r = 100)
INTEGER, PARAMETER :: intkind = SELECTED_INT_KIND(i = 20)
! i = 20 bedeutet Zahlen von -10^i bis 10^i können dargestellt werden
CONTAINS
FUNCTION namenseingabe(eingabeaufforderung)
CHARACTER(len = *), INTENT(IN) :: eingabeaufforderung ! len = * -> übernommene Länge
INTEGER, (KIND=intkind) :: namenseingabe ! innerhalb der Funktion ist eingabe eine
! normal nutzbare Variable, bekommt einen Typ
DO
WRITE(*,*) eingabeaufforderung
READ (*,*) namenseingabe
IF (eingabe > 0) THEN
EXIT
ELSE
WRITE(*,*) "Eingabe fehlerhaft. Bitte nochmal."
END IF
END DO
END FUNCTION
END MODULE
„um das zu nutzen, muss es im Hauptprogramm importiert werden mit USE:“
PROGRAM testprog
USE simpleIO
IMPLICIT NONE
INTEGER :: n
n = eingabe("Hallo, gib eine Zahl ein.")
END PROGRAM
„beim Kompilieren muss beides kompiliert werden, das Modul allerdings
zuerst:
f95 simpleIO.f95 testprog.f95 -o testprog“
This diff is collapsed.
Click to expand it.
Preview
0%
Loading
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Save comment
Cancel
Please
register
or
sign in
to comment