Fortran - Procedimentos
UMA procedureé um grupo de instruções que executam uma tarefa bem definida e podem ser chamadas de seu programa. Informações (ou dados) são passados para o programa de chamada, para o procedimento como argumentos.
Existem dois tipos de procedimentos -
- Functions
- Subroutines
Função
Uma função é um procedimento que retorna uma única quantidade. Uma função não deve modificar seus argumentos.
A quantidade devolvida é conhecida como function value, e é denotado pelo nome da função.
Syntax
A sintaxe para uma função é a seguinte -
function name(arg1, arg2, ....)
[declarations, including those for the arguments]
[executable statements]
end function [name]
O exemplo a seguir demonstra uma função chamada area_of_circle. Ele calcula a área de um círculo com raio 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
Quando você compila e executa o programa acima, ele produz o seguinte resultado -
The area of a circle with radius 2.0 is
12.5663710
Observe que -
Você deve especificar implicit none tanto no programa principal quanto no procedimento.
O argumento r na função chamada é chamado dummy argument.
O resultado Opção
Se você quiser que o valor retornado seja armazenado em algum outro nome que não o nome da função, você pode usar o result opção.
Você pode especificar o nome da variável de retorno como -
function name(arg1, arg2, ....) result (return_var_name)
[declarations, including those for the arguments]
[executable statements]
end function [name]
Subrotina
Uma sub-rotina não retorna um valor, mas pode modificar seus argumentos.
Syntax
subroutine name(arg1, arg2, ....)
[declarations, including those for the arguments]
[executable statements]
end subroutine [name]
Chamando uma subrotina
Você precisa invocar uma sub-rotina usando o call declaração.
O exemplo a seguir demonstra a definição e o uso de uma troca de sub-rotina, que altera os valores de seus argumentos.
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
Quando você compila e executa o programa acima, ele produz o seguinte resultado -
Before calling swap
a = 2.00000000
b = 3.00000000
After calling swap
a = 3.00000000
b = 2.00000000
Especificando a intenção dos argumentos
O atributo intent permite que você especifique a intenção com a qual os argumentos são usados no procedimento. A tabela a seguir fornece os valores do atributo intent -
Valor | Usado como | Explicação |
---|---|---|
dentro | intenção (em) | Usado como valores de entrada, não alterado na função |
Fora | intenção (fora) | Usado como valor de saída, eles são substituídos |
entrada | intenção (inout) | Os argumentos são usados e substituídos |
O exemplo a seguir demonstra o conceito -
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
Quando você compila e executa o programa acima, ele produz o seguinte resultado -
The value of the discriminant is
17.0000000
Procedimentos Recursivos
A recursão ocorre quando uma linguagem de programação permite chamar uma função dentro da mesma função. É chamado de chamada recursiva da função.
Quando um procedimento chama a si mesmo, direta ou indiretamente, é chamado de procedimento recursivo. Você deve declarar este tipo de procedimento precedendo a palavrarecursive antes de sua declaração.
Quando uma função é usada recursivamente, o result opção deve ser usada.
A seguir está um exemplo, que calcula o fatorial para um determinado número usando um procedimento recursivo -
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
Procedimentos Internos
Quando um procedimento está contido em um programa, é chamado de procedimento interno do programa. A sintaxe para conter um procedimento interno é a seguinte -
program program_name
implicit none
! type declaration statements
! executable statements
. . .
contains
! internal procedures
. . .
end program program_name
O exemplo a seguir demonstra o conceito -
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
Quando você compila e executa o programa acima, ele produz o seguinte resultado -
Before calling swap
a = 2.00000000
b = 3.00000000
After calling swap
a = 3.00000000
b = 2.00000000