Fortran系列:
运算符
Fortran
中运算符分为三类,即算术、关系、逻辑。算术运算符有5个,即+, -, *, /, **
,表示加、减、乘、除、乘方。
关系运算符和逻辑运算符,均有等价的字符表示,列表如下
真值条件 | 真值条件 | ||||
---|---|---|---|---|---|
== | .eq. | A和B相等 | /= | .ne. | A和B不等 |
> | .gt. | A > B A>B A>B | < | .lt. | A < B A<B A<B |
>= | .ge. | A ⩾ B A\geqslant B A⩾B | <= | .le. | A ⩽ B A\leqslant B A⩽B |
逻辑运算符共有5个,只能作用于逻辑值.true.
和.false.
与 | 或 | 非 | 同或 | 异或 |
---|---|---|---|---|
.and. | .or. | .not. | .eqv. | .neqv. |
有了运算符,就可以进行计算了,而想要计算,就少不了函数。
函数
fortran
创建函数的方法如下
function func(i) result(j)
integer, intent (in) :: i ! 输入
integer :: j ! 输出
j = i**2 + i**3
end function
program main
implicit none
integer :: i, func
i = 3
print *, i, "^2+", i, "^3=", func(i)
end program
其中func
为函数名,i
为函数的输入参数;result(j)
表示j
是这个函数的返回值,和现代语言的不同之处是,fortran
并没有使用return
这个关键字。
intent(in)
表明变量为只读,之所以要写上这个关键字,乃因fortran
函数在传参时,传递的是地址,换言之,如果函数改变了传递进来的参数的值,会导致这个值发生全局性的改变。用了intent(in)
,将使得这个值不可被更改,保证了传参的严谨性。
后面的主函数main
中,调用了func
,最终结果为
3 ^2+ 3 ^3= 36
关键字result
是可以省略的,但这样写,必须在函数块内,把返回值的名字写为函数的名字。仍以刚刚的函数为例,若不想使用result
,则可写为如下形式
function func(i)
integer, intent (in) :: i ! 输入
integer :: func ! 输出
func = i**2 + i**3
end function
子过程
如果函数没有返回值,那么就是子过程,用关键字subroutine
表示
!testSub.f95
subroutine swap(a,b)
real::a,b,tmp
tmp = a
a = b
b = tmp
end subroutine swap
program testSub
implicit none
real :: a, b
a = 2.0
b = 3.0
call swap(a, b)
print *, "a = ", a
print *, "b = ", b
end program testSub
编译结果如下,看来a
和b
的值果然交换了。
>gfortran testSub.f95
>a.exe
a = 3.00000000
b = 2.00000000
递归
现代主流的编程语言,诸如C/C++,java, c#, python之类的,函数本身就是支持递归的,无需额外的递归标志。但fortran
需要用recursive
修饰的函数,才能进行递归操作,即自己调用自己。
递归函数的另一个问题就是,必须采用result
的方式声明返回值,下面以经典的阶乘为例
! recurTest.f95
recursive function fac (n) result(f)
implicit none
integer :: f
integer, intent (in) :: n
if(n>1) then
f = n * fac(n-1)
else
f = 1
end if
end function fac
program recurTest
implicit none
integer :: a, fac
a = fac(15)
print *, a
end program recurTest
结果如下
1>gfortran recurTest.f95
>a.exe
2004310016
这里涉及到了if()then...else...end if
语句,接下来着重讲解fortran的控制流程。