A procedure is a group of statements that perform a well-defined task and can be invoked from your program. Information (or data) is passed to the calling program, to the procedure as arguments.
There are two types of procedures −
- Functions
- Subroutines
Function
A function is a procedure that returns a single quantity. A function should not modify its arguments.
The returned quantity is known as function value, and it is denoted by the function name.
Syntax
Syntax for a function is as follows −
function name(arg1, arg2, ....)
end function [name]
The following example demonstrates a function named area_of_circle. It calculates the area of a circle with radius r.
program calling_func
real :: a
a = area_of_circle(2.0)
Print *, "The area of a circle with radius 2.0 is"
Print *, a
end program calling_func
! this function computes the area of a circle with radius r
function area_of_circle (r)
! function result
implicit none
! dummy arguments
real :: area_of_circle
! local variables
real :: r
real :: pi
pi = 4 * atan (1.0)
area_of_circle = pi * r**2
end function area_of_circle
When you compile and execute the above program, it produces the following result −
The area of a circle with radius 2.0 is 12.5663710
Please note that −
- You must specify implicit none in both the main program as well as the procedure.
- The argument r in the called function is called dummy argument.
The result Option
If you want the returned value to be stored in some other name than the function name, you can use the result option.
You can specify the return variable name as −
function name(arg1, arg2, ....) result (return_var_name)
end function [name]
Subroutine
A subroutine does not return a value, however it can modify its arguments.
Syntax
subroutine name(arg1, arg2, ....)
end subroutine [name]
Calling a Subroutine
You need to invoke a subroutine using the call statement.
The following example demonstrates the definition and use of a subroutine swap, that changes the values of its arguments.
program calling_func
implicit none
real :: a, b
a = 2.0
b = 3.0
Print *, "Before calling swap"
Print *, "a = ", a
Print *, "b = ", b
call swap(a, b)
Print *, "After calling swap"
Print *, "a = ", a
Print *, "b = ", b
end program calling_func
subroutine swap(x, y)
implicit none
real :: x, y, temp
temp = x
x = y
y = temp
end subroutine swap
When you compile and execute the above program, it produces the following result −
Before calling swap
a = 2.00000000
b = 3.00000000
After calling swap
a = 3.00000000
b = 2.00000000
Specifying the Intent of the Arguments
The intent attribute allows you to specify the intention with which arguments are used in the procedure. The following table provides the values of the intent attribute −
Value | Used as | Explanation |
---|---|---|
in | intent(in) | Used as input values, not changed in the function |
out | intent(out) | Used as output value, they are overwritten |
inout | intent(inout) | Arguments are both used and overwritten |
The following example demonstrates the concept −
program calling_func
implicit none
real :: x, y, z, disc
x = 1.0
y = 5.0
z = 2.0
call intent_example(x, y, z, disc)
Print *, "The value of the discriminant is"
Print *, disc
end program calling_func
subroutine intent_example (a, b, c, d)
implicit none
! dummy arguments
real, intent (in) :: a
real, intent (in) :: b
real, intent (in) :: c
real, intent (out) :: d
d = b * b - 4.0 * a * c
end subroutine intent_example
When you compile and execute the above program, it produces the following result −
The value of the discriminant is
17.0000000
Recursive Procedures
Recursion occurs when a programming languages allows you to call a function inside the same function. It is called recursive call of the function.
When a procedure calls itself, directly or indirectly, is called a recursive procedure. You should declare this type of procedures by preceding the word recursive before its declaration.
When a function is used recursively, the result option has to be used.
Following is an example, which calculates factorial for a given number using a recursive procedure −
program calling_func
implicit none
integer :: i, f
i = 15
Print *, "The value of factorial 15 is"
f = myfactorial(15)
Print *, f
end program calling_func
! computes the factorial of n (n!)
recursive function myfactorial (n) result (fac)
! function result
implicit none
! dummy arguments
integer :: fac
integer, intent (in) :: n
select case (n)
case (0:1)
fac = 1
case default
fac = n * myfactorial (n-1)
end select
end function myfactorial
Internal Procedures
When a procedure is contained within a program, it is called the internal procedure of the program. The syntax for containing an internal procedure is as follows −
program program_name
implicit none
! type declaration statements
! executable statements
. . .
contains
! internal procedures
. . .
end program program_name
The following example demonstrates the concept −
program mainprog
implicit none
real :: a, b
a = 2.0
b = 3.0
Print *, "Before calling swap"
Print *, "a = ", a
Print *, "b = ", b
call swap(a, b)
Print *, "After calling swap"
Print *, "a = ", a
Print *, "b = ", b
contains
subroutine swap(x, y)
real :: x, y, temp
temp = x
x = y
y = temp
end subroutine swap
end program mainprog
When you compile and execute the above program, it produces the following result −
Before calling swap
a = 2.00000000
b = 3.00000000
After calling swap
a = 3.00000000
b = 2.00000000
Leave a Reply