Professional Documents
Culture Documents
F90 Subprograms PDF
F90 Subprograms PDF
Thomas E. Kurtz
Co-Designer of the BASIC language
1
Fall 2010
Functions and Subroutines
zFortran
Fortran 90 has two types of subprograms,
functions and subroutines.
zA Fortran 90 function is a function like those in
C/C++. Thus, a function returns a computed
result via the function name.
name
zIf a function does not have to return a function
value,
l use subroutine.
b ti
2
Function Syntax: 1/3
zA Fortran function,, or function subprogram,
p g ,
has the following syntax:
type FUNCTION function-name (arg1, arg2, ..., argn)
IMPLICIT NONE
[specification part]
[execution part]
p
[subprogram part]
END FUNCTION function-name
ztype is a Fortran 90 type (e.g.,
(e g INTEGER,
INTEGER
REAL, LOGICAL, etc) with or without KIND.
zfunction name is a Fortran 90 identifier
zfunction-name
zarg1, …, argn are formal arguments.
3
Function Syntax: 2/3
zA function is a self-contained unit that receives
some “input” from the outside world via its
formal arguments, does some computations, and
returns the result with the name of the function.
zSomewhere in a function there has to be one or
more assignment statements like this:
function-name = expression
where the result of expression is saved to the
name of the function.
zNote that function-name cannot appear in
the right-hand side of any expression.
4
Function Syntax: 3/3
zIn a type
yp specification,
p , formal arguments
g
should have a new attribute INTENT(IN).
zThe meaningg of INTENT(IN) is that the
function only takes the value from a formal
argument and does not change its content.
zAny statements that can be used in PROGRAM
can also be used in a FUNCTION.
5
Function Example
zNote
Note that functions can have no formal argument.
zBut, () is still required.
Factorial computation Read and return a positive real number
INTEGER FUNCTION Factorial(n) REAL FUNCTION GetNumber()
IMPLICIT NONE IMPLICIT NONE
INTEGER, INTENT(IN) :: n REAL :: Input_Value
INTEGER :: i, Ans DO
WRITE(*,*)
( , ) 'A p
positive number: '
Ans = 1 READ(*,*) Input_Value
DO i = 1, n IF (Input_Value > 0.0) EXIT
Ans = Ans * i WRITE(*,*) 'ERROR. try again.'
END DO END DO
Factorial = Ans GetNumber = Input_Value
END FUNCTION Factorial END FUNCTION GetNumber
6
Common Problems: 1/2
forget
g function type
yp g INTENT(IN) − not an error
forget
FUNCTION DoSomething(a, b) REAL FUNCTION DoSomething(a, b)
IMPLICIT NONE IMPLICIT NONE
INTEGER, INTENT(IN) :: a, b INTEGER :: a, b
DoSomthing = SQRT(a*a + b*b) DoSomthing = SQRT(a*a + b*b)
END FUNCTION DoSomething END FUNCTION DoSomething
incorrect use of function name only the most recent value is returned
REAL FUNCTION DoSomething(a, b) REAL FUNCTION DoSomething(a, b)
IMPLICIT NONE IMPLICIT NONE
INTEGER, INTENT(IN) :: a, b INTEGER, INTENT(IN) :: a, b
DoSomething = a*a + b*b DoSomething = a*a + b*b
DoSomething = SQRT(DoSomething) DoSomething = SQRT(a*a - b*b)
END FUNCTION DoSomething END FUNCTION DoSomething
8
Using Functions
z The use of a user
user-defined
defined function is similar to
the use of a Fortran 90 intrinsic function.
z The following uses function Factorial(n) to
compute the combinatorial coefficient C(m,n) ,
where m and n are actual arguments:
Cmn = Factorial(m)/(Factorial(n)*Factorial(m-n))
WRITE(*,*) Sum(a,b,c)
a b c
11
Argument Association : 3/5
zExpressions
Expressions as actual arguments. Dashed line
boxes are temporary locations.
WRITE(*,*) Sum(a+b,b+c,c)
a+b b+c c
12
Argument Association : 4/5
zConstants
Constants as actual arguments. Dashed line
boxes are temporary locations.
WRITE(*,*) Sum(1, 2, 3)
1 2 3
13
Argument Association : 5/5
zA variable in () is considered as an expression.
p
Dashed line boxes are temporary locations.
14
Where Do Functions Go: 1/2
zFortran
Fortran 90 functions can be internal or external.
zInternal functions are inside of a PROGRAM, the
main program:
PROGRAM program-name
IMPLICIT
C NON
NONE
[specification part]
[execution part]
CONTAINS
[functions]
END PROGRAM program-name
17
Scope Rules: 2/5
zScope Rule #1: The scope of an entity is the
program or function in which it is declared.
PROGRAM Scope_1 Scope of PI, m and n
IMPLICIT NONE
REAL, PARAMETER :: PI = 3.1415926
INTEGER :: m, n
...................
CONTAINS
INTEGER FUNCTION Funct1(k) Scope of k, f and g
IMPLICIT NONE local to Funct1()
INTEGER, INTENT(IN) :: k
REAL :: f, g
..........
END FUNCTION Funct1
REAL FUNCTION Funct2(u, v)
IMPLICIT NONE Scope of u and v
REAL, INTENT(IN) :: u, v local to Funct2()
..........
END FUNCTION Funct2 18
END PROGRAM Scope_1
Scope Rules: 3/5
zScope
p Rule #2 :A global entity is visible to all
contained functions.
PROGRAM Scope_2
IMPLICIT NONE
¾a, b and c are global
INTEGER :: a = 1, b = 2, c = 3 ¾The first Add(a) returns 4
WRITE(*,*) Add(a)
c = 4 ¾Th second
¾The d Add(a)
dd returns
t 5
WRITE(*,*) Add(a)
WRITE(*,*) Mul(b,c) ¾Mul(b,c) returns 8
CONTAINS
INTEGER FUNCTION Add(q)
IMPLICIT NONE Thus, the two Add(a)’s produce different
INTEGER, INTENT(IN) :: q results, even though the formal arguments
Add = q + c
END FUNCTION Add
are the same! This is usually referred to
INTEGER FUNCTION Mul(x, y) as side effect.
IMPLICIT NONE
INTEGER, INTENT(IN) :: x, y
Mul = x * y Avoid using global entities!
END FUNCTION Mul 19
END PROGRAM Scope_2
Scope Rules: 4/5
zScope
p Rule #2 :A global entity is visible to all
contained functions.
Area = s × ( s − a ) × ( s − b) × ( s − c)
22
Example: 2/4
zLOGICAL Function TriangleTest()
g () makes
sure all sides are positive, and the sum of any
two is larger than the third.
23
Example: 3/4
zThis
This function implements the Heron formula.
zNote that a, b and c must form a triangle.
24
Example: 4/4
zHere is the main program!
PROGRAM HeronFormula
IMPLICIT NONE
REAL :: a, b, c, TriangleArea
DO
WRITE(*,*) 'Three sides of a triangle please --> '
READ(*,*) a, b, c
WRITE(*,*) 'Input sides are ', a, b, c
IF (TriangleTest(a, b, c)) EXIT ! exit if they form a triangle
WRITE(*,*) 'Your input CANNOT form a triangle. Try again'
END DO
TriangleArea = Area(a,
Area(a b,
b c)
WRITE(*,*) 'Triangle area is ', TriangleArea
CONTAINS
LOGICAL FUNCTION TriangleTest(a, b, c)
……
END FUNCTION TriangleTest
REAL FUNCTION Area(a, b, c)
……
END FUNCTION Area
25
END PROGRAM HeronFormula
Subroutines: 1/2
zA
A Fortran 90 function takes values from its
formal arguments, and returns a single value
with the function name.
zA Fortran 90 subroutine takes values from its
formal arguments,
arguments and returns some computed
results with its formal arguments.
zA F
Fortran
t 90 subroutine
b ti does
d nott return
t any
value with its name.
26
Subroutines: 2/2
zThe
The following is Fortran 90 subroutine syntax:
SUBROUTINE subroutine-name(arg1,arg2,...,argn)
IMPLICIT NONE
[specification part]
[
[execution
ti part]
t]
[subprogram part]
END SUBROUTINE subroutine
subroutine-name
name
28
The INTENT() Attribute: 2/2
zTwo
Two simple examples:
Am, Gm and Hm are used to return the results
SUBROUTINE Means(a, b, c, Am, Gm, Hm)
IMPLICIT NONE
REAL, INTENT(IN) :: a, b, c
REAL, INTENT(OUT) :: Am, Gm, Hm
Am = (a+b+c)/3.0
Gm = (a*b*c)**(1.0/3.0)
(a*b*c)**(1 0/3 0)
Hm = 3.0/(1.0/a + 1.0/b + 1.0/c)
END SUBROUTINE Means
values of a and b are swapped
SUBROUTINE Swap(a, b)
IMPLICIT NONE
INTEGER, INTENT(INOUT) :: a, b
INTEGER :: c
c = a
a = b
b = c
END SUBROUTINE Swap
29
The CALL Statement: 1/2
zUnlike
Unlike C/C
C/C++ and Java, to use a Fortran 90
subroutine, the CALL statement is needed.
zThe CALL statement may have one of the three
forms:
CALL sub-name(arg1,arg2,…,argn)
sub name(arg1 arg2 argn)
CALL sub-name( )
CALL sub-name
zThe
The last two forms are equivalent and are for
calling a subroutine without formal arguments.
30
The CALL Statement: 2/2
PROGRAM Test PROGRAM SecondDegree
IMPLICIT NONE IMPLICIT NONE
REAL :: a, b REAL :: a, b, c, r1, r2
READ(*,*) a, b LOGICAL :: OK
CALL Swap(a,b) READ(*,*) a, b, c
WRITE(*,*) a, b CALL Solver(a,b,c,r1,r2,OK)
CONTAINS IF (.NOT. OK) THEN
SUBROUTINE Swap(x,y)
Swap(x y) WRITE(* *) “No root”
WRITE(*,*)
IMPLICIT NONE ELSE
REAL, INTENT(INOUT) :: x,y WRITE(*,*) a, b, c, r1, r2
REAL :: z END IF
z = x CONTAINS
x = y SUBROUTINE Solver(a,b,c,x,y,L)
y = z IMPLICIT NONE
END SUBROUTINE Swap REAL INTENT(IN) :: a,b,c
REAL, a b c
END PROGRAM Test REAL, INTENT(OUT) :: x, y
LOGICAL, INTENT(OUT) :: L
………
END SUBROUTINE Solver
END PROGRAM SecondDegree 31
More Argument Association: 1/2
zSince a formal argument
g with the INTENT(OUT)
( )
or INTENT(INOUT) attribute will pass a value
back to the corresponding actual argument, the
actual argument must be a variable.
33
Fortran 90 Modules: 1/4
zOne
One may collect all relevant functions and
subroutines together into a module.
zA module
module, in OO’s
OO s language
language, is perhaps close to
a static class that has public/private information
and methods
methods.
zSo, in some sense, Fortran 90’s module provides
a sortt off object-based
bj t b d rather
th ththan object-
bj t
oriented programming paradigm.
34
Fortran 90 Modules: 2/4
zA
A Fortran 90 module has the following syntax:
MODULE module-name
IMPLICIT NONE
[specification part]
CONTAINS
[internal functions/subroutines]
[ / ]
END MODULE module-name
zThe specification
p p
part and internal functions and
subroutines are optional.
zA module looks like a PROGRAM, except that it
does not have the executable part. Hence, a
main program must be there to use modules.
35
Fortran 90 Modules: 3/4
zExamples:
Examples:
Module SomeConstants does not Module SumAverage does not
p g
have the subprogram p
part have the specification
p p
part
MODULE SomeConstants MODULE SumAverage
IMPLICIT NONE
REAL, PARAMETER :: PI=3.1415926 CONTAINS
REAL PARAMETER :: g = 980
REAL, REAL FUNCTION Sum(a,
S ( b
b, c)
INTEGER :: Counter IMPLICIT NONE
END MODULE SomeConstants REAL, INTENT(IN) :: a, b, c
Sum = a + b + c
END FUNCTION Sum
REAL FUNCTION Average(a, b, c)
IMPLICIT NONE
REAL INTENT(IN) :: a
REAL, a, b
b, c
Average = Sum(a,b,c)/2.0
END FUNCTION Average
END MODULE SumAverage
36
Fortran 90 Modules: 4/4
z The right
g module MODULE DegreeRadianConversion
IMPLICIT NONE
has both the REAL, PARAMETER :: PI = 3.1415926
specification REAL, PARAMETER :: Degree180 = 180.0
part andd CONTAINS
internal REAL FUNCTION DegreeToRadian(Degree)
IMPLICIT NONE
functions
functions. REAL, INTENT(IN) :: Degree
DegreeToRadian = Degree*PI/Degree180
z Normally, this is END FUNCTION DegreeToRadian
the case. REAL FUNCTION RadianToDegree(radian)
IMPLICIT NONE
REAL, INTENT(IN) :: Radian
RadianToDegree = Radian*Degree180/PI
END FUNCTION RadianToDegree
END MODULE DegreeRadianConversion
37
Some Privacy: 1/2
zFortran 90 allows a module to have pprivate and
public items. However, all global entities of a
module, by default, are public (i.e., visible in all
other programs and modules)
modules).
zTo specify public and private, do the following:
PUBLIC :: name-1,
name 1 name
name-2,
2 …, name
name-n
n
PRIVATE :: name-1, name-2, …, name-n
zThe PRIVATE statement without a name makes
all entities in a module private. To make some
entities visible, use PUBLIC.
z
zPUBLIC andd PRIVATE may also l be
b used
d iin
type specification:
INTEGER, PRIVATE :: Sum, Phone_Number 38
Some Privacy: 2/2
z Anyy gglobal entityy MODULE TheForce
(e.g., PARAMETER, IMPLICIT NONE
INTEGER :: SkyWalker, Princess Is this public?
variable, function, REAL, PRIVATE :: BlackKnight
subroutine,
i etc) LOGICAL :: DeathStar
REAL, PARAMETER :: SecretConstant = 0.123456
can be in PUBLIC PUBLIC :: SkyWalker, Princess
or PRIVATE PRIVATE :: VolumeOfDeathStar
PRIVATE :: SecretConstant
statements. CONTAINS
INTEGER FUNCTION VolumeOfDeathStar()
..........
END FUNCTION WolumeOfDeathStar
REAL FUNCTION WeaponPower(SomeWeapon)
..........
END FUNCTION ..........
END MODULE TheForce
MODULE DoSomething
USE SomeConstants, ONLY : g, Counter
IMPLICIT NONE PI is not available
CONTAINS
SUBROUTINE Something(…)
……
END SUBROUTINE Something
S thi
END MODULE DoSomething 41
Using a Module: 3/5
zSometimes,
Sometimes, the “imported”
imported entities from a
MODULE may have identical names with names
g PROGRAM or MODULE.
in the “importing”
p
zIf this happens, one may use the “renaming”
feature of USE.
USE
zFor each identifier in USE to be renamed, use the
f ll i syntax:
following t
name-in-this-PROGRAM => name-in-module
43
Using a Module: 5/5
zTwo USE
S and => examples
p GravityG is the g in the module;
however, g is the “g” in Test
PROGRAM Test
MODULE SomeConstants USE SomeConstants, &
IMPLICIT NONE GravityG => g
REAL, PARAMETER :: PI = 3.1415926 IMPLICIT NONE
REAL,
, PARAMETER :: g = 980 INTEGER :: g
INTEGER :: Counter ……
END MODULE SomeConstants END PROGRAM Test
MODULE Compute
USE SomeConstants, ONLY : PI, g
IMPLICIT NONE
without ONLY, Counter would
REAL :: Counter
appear in MODULE Compute
CONTAINS
causing a name conflict!
……
END MODULE Compute 44
Compile Your Program: 1/4
zSuppose
Suppose a program consists of the main
program main.f90 and 2 modules Test.f90
and Compute.f90.
p In ggeneral,, they
y can be
compiled in the following way:
f90 main.f90 Test.f90 Compute.f90 –o
o main
45
Compile Your Program: 2/4
zSuppose
pp we have modules A,, B,, C,, D and E,, and C
uses A, D uses B, and E uses A, C and D, then a
safest way to compile your program is the
following command:
f90 A.f90 B.f90 C.f90 D.f90 E.f90 main.f90 –o main
49
Example 2
zTrigonometric
Trigonometric functions use degree.
MODULE MyTrigonometricFunctions PROGRAM TrigonFunctTest
IMPLICIT NONE USE MyTrigonometricFunctions
REAL, PARAMETER :: PI = 3.1415926 IMPLICIT NONE
REAL, PARAMETER :: Degree180 = 180.0 REAL :: Begin = -180.0
REAL, PARAMETER :: R_to_D=Degree180/PI REAL :: Final = 180.0
REAL, PARAMETER :: D_to_R
D to R=PI/Degree180
PI/Degree180 REAL :: Step = 10.0
CONTAINS REAL :: x
REAL FUNCTION DegreeToRadian(Degree) x = Begin
IMPLICIT NONE DO
REAL, INTENT(IN)
( ) :: Degree IF (x
( > Final)
i l) EXIT
DegreeToRadian = Degree * D_to_R WRITE(*,*) MySIN(x)
END FUNCTION DegreeToRadian x = x + Step
REAL FUNCTION MySIN(x)
yS ( ) END DO
IMPLICIT NONE END PROGRAM TrigonFunctTest
REAL, INTENT(IN) :: x
MySIN = SIN(DegreeToRadian(x))
END FUNCTION MySIN
SIN
… other functions …
50
END MODULE MyTrigonometricFunctions
INTERFACE Blocks: 1/5
zLegacy
Legacy Fortran programs do not have internal
subprograms in PROGRAMs or MODULEs.
zThese subprograms are in separate files
files. These
are external subprograms that may cause some
compilation problems in Fortran 90
90.
zTherefore, Fortran 90 has the INTERFACE block
f a program or a module
for d l tto k
know th
the ttype off
the subprograms, the intent and type of each
argument,t etc.
t
51
INTERFACE Blocks: 2/5
zConsider
Consider the following triangle area program.
zHow does the main program know the type and
number of arguments of the two functions?
LOGICAL FUNCTION Test(a, b, c) PROGRAM HeronFormula
IMPLICIT NONE IMPLICIT NONE
REAL, INTENT(IN) :: a, b, c … some important here …
LOGICAL :: test1, test2 REAL :: a, b, c
test1 = (a>0.0) .AND. (b>0.0) .AND. (c>0.0) REAL :: TriangleArea
test2 = (a+b>c) .AND. (a+c>b) .AND. (b+c>a) DO
Test = test1 .AND. test2 READ(*,*) a, b, c
END FUNCTION Test IF (Test(a,b,c)) EXIT
END DO
REAL FUNCTION Area(a, b, c) TriangleArea
g = Area(a, b, c)
IMPLICIT NONE WRITE(*,*) TriangleArea
REAL, INTENT(IN) :: a, b, c END PROGRAM HeronFormula
REAL :: s = (a + b + c) / 2.0
Area = SQRT(s*(s-a)*(s-b)*(s-c))
END FUNCTION Area
52
file area.f90 file main.f90
INTERFACE Blocks: 3/5
zAn INTERFACE block has the followingg syntax:
y
INTERFACE
type FUNCTION name(arg-1, arg-2, ..., arg-n)
type, INTENT(IN) :: arg-1
type, INTENT(IN) :: arg-2
..........
type INTENT(IN) :: arg-n
type, arg n
END FUNCTION name
SUBROUTINE name(arg-1, arg-2, …, arg-n)
type, INTENT(IN or OUT or INOUT) :: arg-1
type, INTENT(IN or OUT or INOUT) :: arg-2
..........
type, INTENT(IN or OUT or INOUT) :: arg-n
END SUBROUTINE name
....... other functions/subroutines .......
END INTERFACE
53
INTERFACE Blocks: 4/5
zAll
All external subprograms should be listed
between INTERFACE and END INTERFACE.
zHowever only the FUNCTION and SUBROUTINE
zHowever,
headings, argument types and INTENTs are
needed No executable statements should be
needed.
included.
zTh argumentt names do
zThe d nott have
h to
t be
b identical
id ti l
to those of the formal arguments, because they
“place holders” in an INTERFACE block.
are “place-holders” block
zThus, a main program or subprogram will be
able to know exactly how to use a subprogram.
54
INTERFACE Blocks: 5/5
zReturn to Heron’s formula for triangle
g area.
zThe following shows the INTERFACE block in a
main program.
p g
LOGICAL FUNCTION Test(a, b, c) PROGRAM HeronFormula
IMPLICIT NONE IMPLICIT NONE
REAL INTENT(IN) :: a,
REAL, a b,
b c INTERFACE
LOGICAL :: test1, test2 LOGICAL FUNCTION Test(x,y,z)
test1 = (a>0.0) .AND. (b>0.0) .AND. (c>0.0) REAL, INTENT(IN)::x,y,z
test2 = (a+b>c) .AND. (a+c>b) .AND. (b+c>a)
Test = test1 .AND.
AND test2
END FUNCTION Test
END FUNCTION Test REAL FUNCTION Area(l,m,n)
REAL, INTENT(IN)::l,m,n
REAL FUNCTION Area(a, b, c) END FUNCTION Area
IMPLICIT NONE END INTERFACE
REAL, INTENT(IN) :: a, b, c …… other statements …
REAL :: s END PROGRAM HeronFormula
s = (a + b + c) / 2.0
Area = SQRT(s*(s-a)*(s-b)*(s-c))
END FUNCTION Area
55
file area.f90 file main.f90
The End
56