IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Fortran Discussion :

[Fortran 95] Fin d'une subroutine


Sujet :

Fortran

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre régulier
    Profil pro
    Inscrit en
    Juillet 2008
    Messages
    7
    Détails du profil
    Informations personnelles :
    Localisation : Canada

    Informations forums :
    Inscription : Juillet 2008
    Messages : 7
    Par défaut [Fortran 95] Fin d'une subroutine
    Bonjour,

    J'ai fais un programme en Fortran 95. Je souhaite le réécrire en utilisant des subroutines pour qu'il soit plus lisible.
    J'ai commencé à écrire le début mais j'ai un problème avec l'instruction end subroutine.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    program md
    	call initialize(x,y,z,vx,vy,vz)
    	print*,x(1)
    end program md
     
    subroutine initialize(x,y,z,vx,vy,vz)
    	implicit none
    	integer n,nn,i,j,k,nb
    	real*8 s,s5,rho,fn,k0,cu,sigma,rb,temp,xm,ym,zm
    	parameter(nn=6,n=nn**3,rho=0.8,sigma=1.0,temp=1.35)
    	real*8, dimension(1,n)::x,y,z,vx,vy,vz
    	print*, "computing"
    	S=(real(N)/rho)**(1.0/3.0)
     
    	s5=s/2.0
     
    	fn=float(n)
     
    	k0=0.5*(3.0*fn-4.0)*temp
     
    	cu=2.5*sigma
     
    	rb=(S/4)**2
     
    	! initialize the momentum of the MD box
     
    	xm=0.0
     
    	ym=0.0
     
    	zm=0.0
     
     
    	nb=1
     
    	do i=0,NN-1
     
    		do j=0,NN-1
     
    			do k=0,NN-1
     
    ! use a lattice instead of random for positions
     
     
     
     
     
    				x(nb)=(0.5+real(i))*S/real(nn)
     
    				y(nb)=(0.5+real(j))*S/real(nn)
     
    				z(nb)=(0.5+real(k))*S/real(nn)
     
    				vx(nb)=(-1)**nb*(nb+k)
     
    				vy(nb)=(-1)**nb*(nb+i)
     
    				vz(nb)=(-1)**(nb+1)*(nb+j)
     
    				xm=xm+vx(nb)/fn
     
    				ym=ym+vy(nb)/fn
     
    				zm=zm+vz(nb)/fn
     
     
     
    				nb=nb+1
     
     
     
    			enddo
    		enddo
     
    	enddo
     
    	nb=nb-1
     
    return
    end subroutine initialize
    Losrque je compile avec gfortran, la console me renvoie:
    moleculecall.f95:47.15:

    enddo enddo
    1
    Error: Syntax error in END DO statement at (1)
    moleculecall.f95:52.3:

    end subroutine initialize
    1
    Error: Expecting END DO statement at (1)
    Error: Unexpected end of file in 'moleculecall.f95'
    Je ne comprends vraiment pas. Est-ce que quelqu'un pourrait m'aider ?

  2. #2
    Membre émérite Avatar de genteur slayer
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Juin 2002
    Messages
    710
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juin 2002
    Messages : 710
    Par défaut
    essaye de les écrire normalement pour la norme F95: "end do" au lieu de "enddo" peut-être que le compilo n'aime pas...

    ensuite, vu que tu mets "implicit none" tu devrai avoir des erreurs du fait que tu ne lui dit pas quels sont les paramètres de ta subroutine: utilise l'attribut de variable "intent" que tu mets à "in", "out" ou "inout" :

    esuite cela sert à rien de definir ton tableau à deux dimension 1,n je suppose que tu voulais écrire "1:n"

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    subroutine initialize(x,y,z,vx,vy,vz)
    	implicit none
    	integer n,nn,i,j,k,nb
    	real*8 s,s5,rho,fn,k0,cu,sigma,rb,temp,xm,ym,zm
    	parameter(nn=6,n=nn**3,rho=0.8,sigma=1.0,temp=1.35)
    	real*8, dimension(1,n),intent(out)::x,y,z,vx,vy,vz
    .....
    rien à voir avec ta question, mais tes xm,ym,et zm ont l'air de servir à rien... et je te conseil de mettre ton paramètre nn en paramètre de ta subroutine comme cela tu peut la reutiliser pour des taille différtentes...

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    integer,intent(in) :: nn
     real*8, dimension(:),intent(out) ::x,y,z,vx,vy,vz
    ...
    biensur les tableaux doivent être défini avant l'appel à la sub et avec la bonne taille...

  3. #3
    Membre confirmé
    Inscrit en
    Septembre 2007
    Messages
    32
    Détails du profil
    Informations forums :
    Inscription : Septembre 2007
    Messages : 32
    Par défaut
    Bonjour,
    Je vois deux erreurs qui pourraient expliquer ton problème qui ont un dénominateur commun, à savoir que tes subroutines doivent être "encapsulées" dans ton programme principal. Cela implique tout d'abord que ton "END program" doit se situer après toutes tes subroutines et fonctions. Par ailleurs, ces mêmes subroutines et fonctions doivent être précédées d'un "contains" unique. Cela te donne en gros une structure du type:

    program exemple
    (programme principal)
    contains
    (toutes tes subroutines et fonctions)
    END program exemple

    J'espère avoir pu t'aider.

  4. #4
    Membre régulier
    Profil pro
    Inscrit en
    Juillet 2008
    Messages
    7
    Détails du profil
    Informations personnelles :
    Localisation : Canada

    Informations forums :
    Inscription : Juillet 2008
    Messages : 7
    Par défaut
    Merci pour vos réponses.
    J'ai apporté plusieurs modifications :
    end do au lieu de enddo
    déclarations des tableaux
    utilisation de intent (je n'ai pas encore bien compris à quoi ca servai)
    j'ai inclus la subroutine dans le programme.
    les variables xm,ym,zm me sont utiles pour la suite du programme que je n'ai pas encore modifié.

    Malheuereusement je trouve toujours le meme genre d'erreur.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    program md
    	call initialize(x,y,z,vx,vy,vz,xm,ym,zm)
    	print*,x(1)
     
    contains
    subroutine initialize(x,y,z,vx,vy,vz,xm,ym,zm)
    	implicit none
    	integer n,nn,i,j,k,nb
    	real*8 s,s5,rho,fn,k0,cu,sigma,rb,temp,xm,ym,zm
    	parameter(nn=6,n=nn**3,rho=0.8,sigma=1.0,temp=1.35)
    	real*8, dimension(1:n),intent(out)::x,y,z,vx,vy,vz
    	print*, "computing"
    	S=(real(N)/rho)**(1.0/3.0)
     
    	s5=s/2.0
     
    	fn=float(n)
     
    	k0=0.5*(3.0*fn-4.0)*temp
     
    	cu=2.5*sigma
     
    	rb=(S/4)**2
     
    	! initialize the momentum of the MD box
     
    	xm=0.0
     
    	ym=0.0
     
    	zm=0.0
     
     
    	nb=1
     
    	do i=0,NN-1
     
    		do j=0,NN-1
     
    			do k=0,NN-1
     
    ! use a lattice instead of random for positions
     
     
     
     
     
    				x(nb)=(0.5+real(i))*S/real(nn)
     
    				y(nb)=(0.5+real(j))*S/real(nn)
     
    				z(nb)=(0.5+real(k))*S/real(nn)
     
    				vx(nb)=(-1)**nb*(nb+k)
     
    				vy(nb)=(-1)**nb*(nb+i)
     
    				vz(nb)=(-1)**(nb+1)*(nb+j)
     
    				xm=xm+vx(nb)/fn
     
    				ym=ym+vy(nb)/fn
     
    				zm=zm+vz(nb)/fn
     
     
     
    				nb=nb+1
     
     
     
    			end do
    		end do
     
    	end do
     
    	nb=nb-1
     
    return
    end subroutine initialize
    end program md
    je tape: gfortran -o moleculecallout moleculecall.f95

    et la console renvoie:
    moleculecall.f95:46.14:

    end do end do
    1
    Error: Syntax error in END DO statement at (1)
    moleculecall.f95:51.3:

    end subroutine initialize
    1
    Error: Expecting END DO statement at (1)
    moleculecall.f95:52.3:

    end program md
    1
    Error: Expecting END DO statement at (1)
    Error: Unexpected end of file in 'moleculecall.f95'
    On dirait qu'il ne reconnait pas les instructions end do.

  5. #5
    Membre confirmé
    Inscrit en
    Septembre 2007
    Messages
    32
    Détails du profil
    Informations forums :
    Inscription : Septembre 2007
    Messages : 32
    Par défaut
    Bonjour,
    Un élément important lors de la construction de subroutines est de bien distinguer ce qui relève du programme principal et ce qui est de l'ordre de la subroutine. A titre d'exemple, tu appelles des tableaux dans ta subroutine que tu dois utiliser dans le programme principal (x, y, z, etc.). C'est là qu'ils doivent être déclarés, et leurs dimensions sont passées implicitement à la subroutine.
    Un petit élément utile est le "implicit none" à placer avant la déclaration des variables. Ça évite le désagrément des variables non déclarées...
    Voici une version qui semble tourner (pas optimale, mais ça t'illustrera mon propos):

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    program md
            implicit none
     
            integer:: nn,n
    	real*8 :: xm,ym,zm,rho,sigma,temp
    	real*8, allocatable, dimension(:)::x,y,z,vx,vy,vz
     
            nn=6
            n=nn**3
            rho=0.8
            sigma=1.0
            temp=1.35
            allocate(x(n),y(n),z(n),vx(n),vy(n),vz(n))
    	call initialize(x,y,z,vx,vy,vz,xm,ym,zm,nn,n,rho,temp)
    	print*,x(1)
     
    contains
      subroutine initialize(x,y,z,vx,vy,vz,xm,ym,zm,nn,n,rho,temp)
        implicit none
        integer ::n,nn,i,j,k,nb
        real*8 ::s,s5,rho,fn,k0,cu,sigma,rb,temp,xm,ym,zm
        real*8, dimension(:),intent(out)::x,y,z,vx,vy,vz
        print*, "computing"
        S=(real(n)/rho)**(1.0/3.0)
        s5=s/2.0
        fn=float(n)
        k0=0.5*(3.0*fn-4.0)*temp
        cu=2.5*sigma
        rb=(S/4)**2
     
        ! initialize the momentum of the MD box
        xm=0.0
        ym=0.0
        zm=0.0
        nb=1
        do i=0,nn-1
           do j=0,nn-1
              do k=0,nn-1
                 ! use a lattice instead of random for positions
                 x(nb)=(0.5+real(i))*S/real(nn)
                 y(nb)=(0.5+real(j))*S/real(nn)
                 z(nb)=(0.5+real(k))*S/real(nn)
                 vx(nb)=(-1)**nb*(nb+k)
                 vy(nb)=(-1)**nb*(nb+i)
                 vz(nb)=(-1)**(nb+1)*(nb+j)
                 xm=xm+vx(nb)/fn
                 ym=ym+vy(nb)/fn
                 zm=zm+vz(nb)/fn
     
                 nb=nb+1
              end do
           end do
        end do
        nb=nb-1
     
        return
      end subroutine initialize
     
    end program md
    A toi de voir ce qui relève de la subroutine pure (variables locales) ou de l'ensemble de ton programme.

Discussions similaires

  1. Fortran : Debugger seulement une subroutine (CodeBlock)
    Par AeonTyphon dans le forum Fortran
    Réponses: 1
    Dernier message: 04/04/2011, 17h15
  2. Problème de performance d'une subroutine FORTRAN
    Par Kercheur dans le forum Fortran
    Réponses: 3
    Dernier message: 15/02/2011, 16h54
  3. Réponses: 4
    Dernier message: 27/11/2008, 18h02
  4. Utiliser une subroutine fortran en C
    Par chaponinho dans le forum Linux
    Réponses: 1
    Dernier message: 28/04/2008, 20h08
  5. [Fortran 77] Déclaration dans une subroutine
    Par feynman dans le forum Fortran
    Réponses: 4
    Dernier message: 18/04/2008, 17h41

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo