Seb
Seb

Reputation: 33

Accessing variable in main program from external subroutine

I'm trying to solve a maximum likelihood problem in Fortran using the NAG optimization library, but I'm running into problems accessing the variables in the main program from the external subroutines funct and hess (see pseudo-code below). What is the best way to pass variables (e.g. b) from the main program to such routines, given that I cannot pass them directly as arguments (a restriction of the NAG library). I have tried to implement COMMON blocks, but without much succes.

MODULE user_parameters
    ! Define the user parameters
    INTEGER, PARAMETER :: a = 100
    ... other parameters
END MODULE user_parameters


MODULE process_data
    USE user_parameters

    ! Define some other variables
    INTEGER :: b
    ... other variables

CONTAINS

    SUBROUTINE read_data
        ... read the data (e.g. alter value of b)
    END SUBROUTINE read_data

    SUBROUTINE clean_data
        ... clean the data (e.g. alter value of b)
    END SUBROUTINE clean_data
END MODULE process_data


MODULE maximum_likelihood
    USE user_parameters
    USE process_data

CONTAINS

    SUBROUTINE funct
        ... returns the LL's function value and gradient
    END SUBROUTINE funct

    SUBROUTINE hess
        ... returns the LL's hessian
    END SUBROUTINE hess
END MODULE maximum_likelihood


PROGRAM estimation
    USE user_parameters
    USE process_data
    USE maximum_likelihood
    EXTERNAL funct, hess

    CALL read_data
    CALL clean_data

    ! Call minimization routine
    CALL E04LBF(funct, hess)

END PROGRAM estimation

Upvotes: 1

Views: 817

Answers (1)

norio
norio

Reputation: 3892

How about writing your module maximum_likelihood something as following?

MODULE maximum_likelihood
    IMPLICIT NONE
    PRIVATE
    PUBLIC init, fin, funct, hess

    INTEGER, SAVE                         :: aa, bb
    REAL, DIMENSION(:), ALLOCATABLE, SAVE :: vv

CONTAINS

    SUBROUTINE init(aa_arg, bb_arg, vv_arg)
        ! set values module variables
    END SUBROUTINE init

    SUBROUTINE fin()
        deallocate(vv) 
    END SUBROUTINE fin

    SUBROUTINE funct
        ... returns the LL's function value and gradient
        ! using the values of aa, bb, and/or vv
    END SUBROUTINE funct

    SUBROUTINE hess
        ... returns the LL's hessian
        ! using the values of aa, bb, and/or vv
    END SUBROUTINE hess

END MODULE maximum_likelihood

Then, the main program will look like

PROGRAM estimation
    USE maximum_likelihood, ONLY: init, fin, funct, hess

    ! read values for the parameters aaa, bbb, vvv

    ! set these values in the module variables in maximum_likelihood
    CALL init(aaa, bbb, vvv)

    ! Call minimization routine
    CALL E04LBF(funct, hess)

    ! clean up the module variables in maximum_likelihood
    CALL fin()

END PROGRAM estimation

Upvotes: 1

Related Questions