在Windows上使用GFortran在Matlab中创建Mex文件

时间:2017-03-17 21:17:23

标签: matlab fortran gfortran mex

我正在努力将一个Fortran例程添加到Matlab中(通过Mex函数)。我只是想编写一个简单的程序来理解Matlab,Mex和Fortran之间的链接。

我写了一个简单的程序,其值为xy,将它们相加并输出z。但是,当我在编译后尝试在Matlab中运行时,Matlab只是在没有解释的情况下崩溃。知道我在这里做错了什么吗?

! MEX FILE EXAMPLE
!


module yprime_mod ! test module for gnumex and g95
  use mexinterface
contains
  subroutine yprime(x, y, z) ! subroutine yprime(z, t, y, error, x)
    implicit none
    double precision :: x, y, z
    intent(in)  :: x, y
    intent(out) :: z
    ! 
    z=x+y;
  end subroutine yprime
end module yprime_mod

subroutine mexfunction(nlhs, plhs, nrhs, prhs)
  use yprime_mod
  implicit none
  integer :: nlhs, nrhs, plhs(nlhs), prhs(nrhs)
  double precision, pointer :: xp, yp, z
  !
  if (nrhs /= 2) call mexerrmsgtxt('yprime requires two input arguments')
  if (nlhs > 1) call mexerrmsgtxt('yprime requires one output argument')
  call c_f_pointer(mxgetpr(prhs(1)), xp)  ! assign pointers to parameters
  call c_f_pointer(mxgetpr(prhs(2)), yp)
  call c_f_pointer(mxgetpr(plhs(1)), z)
  call yprime(xp, yp, z)
end subroutine mexfunction

1 个答案:

答案 0 :(得分:0)

在不了解Fortran的情况下,我遵循了基本的例子,并且它正在运作。

我对使用c_f_pointer一无所知(可能与崩溃有关) 我认为代码很可能崩溃,因为你忘了调用plhs(1) = mxCreateDoubleMatrix(mrows,ncols,0)来为返回参数创建矩阵。

以下是修改后的代码:

! MEX FILE EXAMPLE
!

#include "fintrf.h"

module yprime_mod ! test module for gnumex and g95
  !use mexinterface
contains
  subroutine yprime(x, y, z) ! subroutine yprime(z, t, y, error, x)
    implicit none
    double precision :: x, y, z
    intent(in)  :: x, y
    intent(out) :: z
    ! 
    z=x+y;
  end subroutine yprime
end module yprime_mod
!   
!    
subroutine mexfunction(nlhs, plhs, nrhs, prhs)
  use yprime_mod
  implicit none
  !integer :: nlhs, nrhs, plhs(nlhs), prhs(nrhs)
  !double precision, pointer :: xp, yp, zp
  !double precision x, y, z 

  !mexFunction arguments:
  mwPointer plhs(*), prhs(*)
  integer nlhs, nrhs

  !Function declarations:
  mwPointer mxGetPr
  mwPointer mxCreateDoubleMatrix
  mwPointer mxGetM, mxGetN

  !Pointers to input/output mxArrays:
  mwPointer xp, yp, zp

  !Arguments for computational routine:
  real*8 x, y, z

  if (nrhs /= 2) call mexerrmsgtxt('yprime requires two input arguments')
  if (nlhs > 1) call mexerrmsgtxt('yprime requires one output argument')

  !To points to the input matrices data, use the mxGetPr function.
  xp = mxGetPr(prhs(1))
  yp = mxGetPr(prhs(2))

  !Create Fortran arrays from the input arguments.
  call mxCopyPtrToReal8(xp,x,1)
  call mxCopyPtrToReal8(yp,y,1)

  !Create scalar for the return argument.
  plhs(1) = mxCreateDoubleMatrix(1,1,0)

  !Use the mxGetPr function to assign the y_ptr argument to plhs(1).
  zp = mxGetPr(plhs(1))

  !call c_f_pointer(mxgetpr(prhs(1)), xp)  ! assign pointers to parameters
  !call c_f_pointer(mxgetpr(prhs(2)), yp)
  !call c_f_pointer(mxgetpr(plhs(1)), z)

  !call yprime(xp, yp, zp)

  !Perform Calculation
  call yprime(x, y, z)

  !Copy Results to Output Argument
  call mxCopyReal8ToPtr(z,zp,1)

end subroutine mexfunction

我使用英特尔编译器进行编译,并在Visual Studio中调试代码(一步一步) mex文件正常运行...