在 Fortran 中使用非线性求解器:SNSQE - SLATEC

Using nonlinear solver in Fortran: SNSQE - SLATEC

我想弄清楚如何在 Fortran 中调用求解器来求解一些 n 维非线性方程。我遇到了 SLATEC library which has some nonlinear solver routines, and the one I'm trying to use is SNSQE。 (另外:也许你知道一些 better/easier 求解器可以使用。请告诉!)

我的示例代码试图解决一个简单的二维问题。您可以手动解决它,但关键是要弄清楚求解器是如何工作的。代码在这里:

program test
  implicit none

  ! declarations
  real :: theta0, x0, d(2), theta_ss(2)
  integer, parameter :: nprint=0, n=2, iopt=2, lwa = 180
  integer :: info
  real :: tol, fvec(2), jac(2), wa(lwa)

  ! set parameters
  theta_ss = 3.
  tol = .0000001

  ! make sure my function works
  d = FNC(theta_ss)
  write(*,*) theta_ss
  write(*,*) d

  ! call the solver and write output
  call SNSQE( FNC, jac, iopt, n, theta_ss, fvec, tol, nprint, info, wa, lwa )
  write(*,*) theta_ss, fvec, tol, info

contains 

  function FNC(x)
    real, intent(in) :: x(2)
    real :: FNC(2)

    FNC(1) =  x(1)**2 - 1
    FNC(2) =  x(2)**3 - 10

  end function FNC    
end program test

我用以下内容编译:

ifort -fast test_solver.f90 -o test -lslatec

我运行生成的可执行文件./test并得到:

3.000000       3.000000    
8.000000       17.00000 
forrtl: severe (174): SIGSEGV, segmentation fault occurred

所以我的函数 FNC 可以独立运行,但不能在 SNSQE 中运行。我所有的输入都是正确的类型和正确的顺序。我试过用不同的方式编写 FNC 函数。我不确定为什么它不起作用。

运行 OSX - Yosemite,英特尔 Fortran 编译器,SLATEC 是使用相同的编译器从源代码编译的。

用户提供的函数不是SNSQE所期望的。从链接文件中的注释可以看出 FCN 必须是以下形式的子例程:

SUBROUTINE FCN(N,X,FVEC,IFLAG)
  INTEGER N,IFLAG
  REAL X(N),FVEC(N)
  ! ----------
  ! Calculate the functions at X and
  ! return this vector in FVEC.
  ! ----------
END SUBROUTINE