Fortran二分法程序编译错误求助:实参与哑参特性不匹配
二分法Fortran程序编译错误排查与解决
问题描述
用户编写了一个用二分法求解函数根的Fortran程序,编译时出现参数特征不匹配的错误,程序代码如下:
MODULE RootSubs TYPE RootType REAL root,f_root,interval END TYPE RootType CONTAINS !1---------------------------------------------------- SUBROUTINE Bisection(G,XL,XR,n_intervals,roots) !Set up intervals for finding roots with bisection method. IMPLICIT NONE REAL, INTENT(IN) :: XL,XR INTEGER, INTENT(IN) :: n_intervals TYPE (RootType), INTENT(OUT) :: roots (n_intervals) REAL dx,xa,xb INTEGER i !------------------------------- INTERFACE REAL FUNCTION G(x) REAL, INTENT(IN) :: x END FUNCTION G END INTERFACE !------------------------------ dx=(XR-XL)/n_intervals DO i=1,n_intervals xa=XL+REAL(i-1)*dx xb=XL+REAL(i)*dx IF (G(xa)*G(xb) < 0.) THEN CALL Bisect(G,xa,xb,roots(i)%root,roots(i)%f_root, & roots(i)%interval) ELSE roots(i)%root=0.; roots(i)%f_root=0.; roots(i)%interval=0. END IF END DO END SUBROUTINE Bisection SUBROUTINE Bisect(G,xa,xb,x_mid,f_mid,final_interval) IMPLICIT NONE REAL, INTENT (INOUT) :: xa,xb REAL, INTENT(OUT) :: x_mid,f_mid,final_interval LOGICAL hit REAL, PARAMETER:: epsilon_x=1e-5,epsilon_f=1e-5 !------------------------------- INTERFACE REAL FUNCTION G(x) REAL, INTENT(IN) :: x END FUNCTION G END INTERFACE !------------------------------ x_mid=(xb+xa)/2. hit=.false. f_mid=G(x_mid) DO WHILE (((xb-xa) > epsilon_x).AND. & (ABS(f_mid) > epsilon_f).AND.(.NOT. hit)) IF (f_mid == 0.) THEN hit=.true. ELSE IF (G(xa)*f_mid < 0) THEN xb=x_mid ELSE IF (G(xb)*f_mid < 0) THEN xa=x_mid ELSE PRINT *, 'Unexplained error!' END IF x_mid=(xb+xa)/2. f_mid=G(x_mid) final_interval=xb-xa END DO END SUBROUTINE Bisect !-------------------------- END MODULE RootSubs !============================== MODULE FunctionDefinition CONTAINS !----------------------- REAL FUNCTION G(x) IMPLICIT NONE REAL x G=5.d0*x**3-2.d0*x**2+3.d0 END FUNCTION G !---------------------------------- END MODULE FunctionDefinition !================================== PROGRAM GetRoots !MS-DOS file name ROOTS.F90 USE RootSubs, ONLY : RootType,Bisection USE FunctionDefinition, ONLY : G IMPLICIT NONE INTEGER, PARAMETER :: n_intervals=10 TYPE (RootType) roots (n_intervals) INTEGER i CALL Bisection(G,-10.,0.,n_intervals,roots) DO i=1,n_intervals PRINT *,i,roots(i)%root,roots(i)%f_root,roots(i)%interval END DO END PROGRAM
编译错误信息
FIG12-12.F90(96): error #7061: The characteristics of dummy argument 1 of the associated actual procedure differ from the characteristics of dummy argument 1 of the dummy procedure. [G] CALL Bisection(G,-10.,0.,n_intervals,roots) ---------------^ compilation aborted for FIG12-12.F90 (code 1)
错误原因
错误核心是实际传递的函数G与子程序接口中声明的G参数特征不匹配:
- 在
RootSubs模块的Bisection、Bisect子程序的接口块中,函数G的参数x被声明为REAL, INTENT(IN); - 但在
FunctionDefinition模块中定义的G函数,参数x仅声明为REAL,未指定INTENT(IN)属性。
Fortran对过程(函数/子程序)的接口匹配要求严格,参数的属性必须完全一致,否则编译器会判定特征不匹配,终止编译。
解决方法
修改FunctionDefinition模块中的G函数,给参数x添加INTENT(IN)属性,修改后的代码片段如下:
MODULE FunctionDefinition CONTAINS !----------------------- REAL FUNCTION G(x) IMPLICIT NONE REAL, INTENT(IN) :: x ! 新增INTENT(IN)属性,与接口声明匹配 G=5.d0*x**3-2.d0*x**2+3.d0 END FUNCTION G !---------------------------------- END MODULE FunctionDefinition
补充优化建议
当前代码中G函数使用了双精度常量(5.d0、2.d0),但返回值和参数都是单精度REAL,会触发隐式精度转换。如果需要更高精度的计算,可以统一将所有REAL替换为REAL(8)或DOUBLE PRECISION,保持精度一致性。
内容的提问来源于stack exchange,提问作者Lucas Morais
相关产品推荐
相关产品推荐

