Започвам тази тема, за да помоля за помощ при разрешаване на проблем, който може да идва от грешната ми спецификация на функционален интерфейс, но не знам как да го поправя.
Съобщението за грешка, на което се натъкнах, е кратко и просто гласи: „Незаконен брой или тип аргументи за lnsrch – аргументите на fmin и func не съвпадат.“
Дефиницията на LNSRCH
, FMIN
и FUNC
ще бъде ясна в съдържанието по-долу.
Оригиналният програмен код е съкратен, за да илюстрира моето намерение, както е показано по-долу. Състои се от три части: основна програмна единица, наречена MAIN
, модул, наречен MODEL
, и модул, наречен NEWTON
). Трябва да можете да възпроизведете съобщението за грешка само като използвате следния файл във формат .f90: връзка
Модул MODEL
просто дефинира проста система от уравнения в две променливи --- y(1)=x(1); y(2)=x(2) ---в подпрограмата FUNC_SYSTEM1
. Модул MODEL
също съдържа абстрактен интерфейс за бъдещо разширение, така че мога просто да накарам показалеца FUNCV
да препраща към всяка друга система от уравнения от същия вид като настоящата примерна система от уравнения FUNC_SYSTEM1
, с изключение само на броя на променливите на системата от уравнения .
MODULE model
IMPLICIT NONE
REAL, DIMENSION(:), POINTER :: fmin_fvecp
ABSTRACT INTERFACE
FUNCTION function_system_template(x) RESULT(y)
REAL, DIMENSION(:), INTENT(IN) :: x
REAL, DIMENSION(SIZE(x)) :: y
END FUNCTION
END INTERFACE
PROCEDURE(function_system_template), POINTER :: funcv
CONTAINS
FUNCTION func_system1(x) Result(y)
IMPLICIT NONE
REAL, DIMENSION(:), INTENT(IN) :: x
REAL, DIMENSION(size(x)) :: y
y(1)=x(1)
y(2)=x(2)
END FUNCTION func_system1
END MODULE model
Модул NEWTON
дефинира връзката между три подпрограми, които са ключови за изчисленията на програмата: BROYDEN
ще извика FMIN
, за да получи сумата от квадратите на x(1) и x(2); едновременно, в FMIN
, векторът на x(1) и x(2) се присвоява на указател на масив, наречен FMIN_FVECP
. Този указател на масив трябва да се използва за извършване на странични изчисления във функцията LNSRCH
.
MODULE newton
USE model
IMPLICIT NONE
REAL, DIMENSION(:), POINTER :: fmin_fvecp
CONTAINS
SUBROUTINE broyden(x,fmin_fvecp,funcv)
IMPLICIT NONE
REAL, DIMENSION(:), INTENT(IN) :: x
REAL, DIMENSION(size(x)), TARGET :: y
REAL, DIMENSION(:), POINTER :: fmin_fvecp
PROCEDURE(function_system_template), POINTER :: funcv
fmin_fvecp=>y
print*,fmin(x,fmin_fvecp,funcv) ! Get the sum of squares
print*,fmin_fvecp ! Show the vector x(1) and x(2)
print*,lnsrch(x,fmin,fmin_fvecp,funcv) ! Show the figure calculated in LNSRCH
END SUBROUTINE broyden
FUNCTION fmin(x,fmin_fvecp,funcv) RESULT(y)
IMPLICIT NONE
REAL, DIMENSION(:), INTENT(IN) :: x
REAL, DIMENSION(:), POINTER :: fmin_fvecp
PROCEDURE(function_system_template), POINTER :: funcv
REAL :: y
fmin_fvecp=funcv(x) ! The value of FMIN_FVECP is assigend
fmin=dot_product(fmin_fvecp,fmin_fvecp)! when FMIN is called by BROYDEN
END FUNCTION fmin
FUNCTION lnsrch(x,func,a_fvecp,b_funcv) RESULT(y)
IMPLICIT NONE
REAL, DIMENSION(:), INTENT(IN) :: x
REAL, DIMENSION(:), POINTER :: a_fvecp
PROCEDURE(function_system_template), POINTER :: b_funcv
INTERFACE
FUNCTION func(x,fvecp,funcp)
IMPORT :: function_system_template
IMPLICIT NONE
REAL, DIMENSION(:), INTENT(IN) :: x
REAL :: func
REAL, DIMENSION(:), POINTER :: fvecp
PROCEDURE(function_system_template), POINTER :: funcp
END FUNCTION
END INTERFACE
REAL, DIMENSION(SIZE(x)) :: y
y=x+a_fvecp+b_funcv(x)+1000.
END FUNCTION lnsrch
END MODULE newton
Основната програмна единица е дефинирана, както следва:
PROGRAM main
USE model
USE newton
IMPLICIT NONE
REAL, DIMENSION(:), allocatable :: x
allocate(x(2))
x=[1.,2.] ! The input arguments to be passed into
funcv=>func_system1 ! the equation system, FUNC_SYSTEM1.
call broyden(x,fmin_fvecp,funcv) ! Call BROYDEN to do the subsequent calcualtion
deallocate(x)
END PROGRAM main
Извинете за дългия пост. Благодаря за времето, което прочетохте въпроса ми. Очакваме с нетърпение всяка информация за заобикаляне на съобщението за грешка. Благодаря.
Лий
fmin_fvecp1
и в двата модула, което е конфликт, тъй като и двата се използват в програмата. Иматеfmin=..
вfunction fmin
, но не иy=...
, което е проблем, тъй като сте деклариралиresult (y)
. - person M. S. B.   schedule 29.04.2013