- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Hello,
I have a main program and two modules, where one module defines input used throughout the subroutines of the main program (call it commons) and the other one evaluates a function (call it mixture_mod). From the main program I call a subroutine in mixture_mod and pass some input. I would like that input to be "global" for the mixture_mod, because the subroutine uses another subroutine with the same input. The variables in two modules have the same names, and I believe that IMPLICIT NONE and PRIVATE should isolate the input variables in mixture_mod from the rest of the program. It seems not to be the case, as I receive the errors:
error #6279: A specification expression object must be a dummy argument, a COMMON block object, or an object accessible through host or use association [NVR]
error #6841: An automatic object must not appear in the specification part of a module.
I am wondering if there is a way to isolate variable names in mixture_mod so that they do not clash with the same names used in the main program? A solution could be to rename the variables, but I am not sure this is sufficient as I would like mixture_mod to be able to stand along from the rest of the program. Or maybe this is not what causes the errors, but what then?
Thank you in advance. The code is provided.
MODULE MIXTURE_MOD
IMPLICIT NONE
PRIVATE
PUBLIC :: getmixture
INTEGER(4) :: nvr,nfk,nx
REAL(8) :: x(nvr,nx),qw(nx),logphi(nx)
CONTAINS
SUBROUTINE getmixture(nvr0,nx0,qx,qw0,logphi0,nfk0,th)
INTEGER(4),INTENT(IN) :: nvr0,nx0
INTEGER(4),INTENT(OUT) :: nfk0
REAL(8),INTENT(IN) :: qx(nvr0,nx0),qw0(nx0),logphi0(nx0)
REAL(8),ALLOCATABLE,INTENT(OUT) :: th(:)
REAL(8) :: th0(6),fstar
INTEGER(4) :: k
nvr=nvr0; nx=nx0; x=qx; qw=qw0; logphi=logphi0;
nfk=1; k=6; th0=0d0;
CALL fcn(k,th0,fstar);
nfk0=nfk;
ALLOCATE(th(6)); th=th0;
END SUBROUTINE getmixture
SUBROUTINE fcn(npk,th_f,fd)
IMPLICIT NONE
INTEGER(4), INTENT(IN) :: npk
REAL(8), INTENT(IN) :: th_f(npk)
REAL(8), INTENT(OUT) :: fd
!Uses specification part of the module as intermediate input
fd=1d0;
END SUBROUTINE fcn
END MODULE MIXTURE_MOD
MODULE commons
IMPLICIT NONE
SAVE
INTEGER(4) :: nvr,nfk,nk,nx
REAL(8),ALLOCATABLE :: qw(:),x(:,:),logphi(:)
END MODULE commons
PROGRAM test
USE commons
USE MIXTURE_MOD
IMPLICIT NONE
REAL(8),ALLOCATABLE :: th1(:)
nvr=2; nk=5 ; nx=nk**nvr
ALLOCATE(qw(nx),x(nvr,nx),logphi(nx))
x=1d0; qw=1d0; logphi=1d0
CALL getmixture(nvr,nx,x,qw,logphi,nfk,th1)
END PROGRAM test
Link Copied
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
The problem you have here is not the names but that you've declared module variables x, qw and logphi as arrays whose bounds are other module variables. This doesn't work - module variables are static and come into existence when the program starts - you can't later assign values to the bounds.
What you want to do here instead is make these arrays ALLOCATABLE with deferred-shape bounds, like this:
REAL(8), ALLOCATABLE :: x(:,:),qw(:),logphi(:)
and then allocate them to the desired size when the program starts (probably by calling a procedure in the module to do it.)
As for names, you're right that there can be a conflict if a procedure that USEs the module declares local variables of the same name. If the module variables are used only in the module, then make them PRIVATE. Otherwise consider naming them with a prefix that makes them unique.
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
I see now where my mistake was. Indeed the dimension of x,qw,logphi was based not on parameters but variable input. Thanks!
- Subscribe to RSS Feed
- Mark Topic as New
- Mark Topic as Read
- Float this Topic for Current User
- Bookmark
- Subscribe
- Printer Friendly Page