CCL Home Page
Up Directory CCL f.31
********************************************************************************
** FICHE F.31.  CONSTANT-NPT MOLECULAR DYNAMICS - CONSTRAINT METHOD           **
** This FORTRAN code is intended to illustrate points made in the text.       **
** To our knowledge it works correctly.  However it is the responsibility of  **
** the user to test it, if it is to be used in a research application.        **
********************************************************************************



        PROGRAM EVAMOR

        COMMON / BLOCK1 / RX, RY, RZ, RX1, RY1, RZ1,
     :                    RX2, RY2, RZ2, RX3, RY3, RZ3,
     :                    PX, PY, PZ, PX1, PY1, PZ1,
     :                    PX2, PY2, PZ2, PX3, PY3, PZ3,
     :                    FX, FY, FZ
        COMMON / BLOCK2 / BOX, BOX1, BOX2, BOX3

C    *******************************************************************
C    ** CONSTANT-NPT MOLECULAR DYNAMICS USING CONSTRAINT ALGORITHM.   **
C    **                                                               **
C    ** THE MODIFIED EQUATIONS OF MOTION ARE AS FOLLOWS:              **
C    **       R1 = P/M + CHI*R                                        **
C    **       P1 = F - CHI*P - XI*P                                   **
C    **       V1 = 3*V*CHI                                            **
C    ** WHERE R1 IS THE TIME DERIVATIVE OF POSITION R                 **
C    ** P1 IS THE TIME DERIVATIVE OF MOMENTUM P                       **
C    ** V1 IS THE TIME DERIVATIVE OF VOLUME V                         **
C    ** AND CHI AND XI ARE LAGRANGE MULTIPLIERS                       **
C    **       CHI = ( - SUM( (R.P) X / (R.R) ) ) / ( SUM(X) + 9PV )   **
C    **       XI  = SUM(P.F) / SUM(P.P) - CHI                         **
C    ** HERE TERMS LIKE (P.F) ARE SCALAR PRODUCTS OVER PAIR TERMS AND **
C    ** PV STANDS FOR PRESSURE * VOLUME.                              **
C    ** WE SOLVE THESE EQUATIONS BY A GEAR 4-VALUE METHOD FOR FIRST   **
C    ** ORDER DIFFERENTIAL EQUATIONS                                  **
C    **                                                               **
C    ** REFERENCES:                                                   **
C    **                                                               **
C    ** EVANS AND MORRISS, CHEM PHYS 77, 63, 1983.                    **
C    ** EVANS AND MORRISS, COMPUT PHYS REP 1, 297, 1984.              **
C    **                                                               **
C    ** PRINCIPAL VARIABLES:                                          **
C    **                                                               **
C    ** INTEGER N                             NUMBER OF MOLECULES     **
C    ** REAL    DT                            TIMESTEP                **
C    ** REAL    RX(N),RY(N),RZ(N)             POSITIONS               **
C    ** REAL    RX1(N),RY1(N),RZ1(N)          FIRST DERIVATIVES       **
C    ** REAL    RX2(N),RY2(N),RZ2(N)          SECOND DERIVATIVES      **
C    ** REAL    RX3(N),RY3(N),RZ3(N)          THIRD DERIVATIVES       **
C    ** REAL    PX(N),PY(N),PZ(N)             MOMENTA                 **
C    ** REAL    PX1(N),PY1(N),PZ1(N)          FIRST DERIVATIVES       **
C    ** REAL    PX2(N),PY2(N),PZ2(N)          SECOND DERIVATIVES      **
C    ** REAL    PX3(N),PY3(N),PZ3(N)          THIRD DERIVATIVES       **
C    ** REAL    BOX,BOX1,BOX2,BOX3            BOX LENGTH AND DERIVS   **
C    ** REAL    FX(N),FY(N),FZ(N)             TOTAL FORCES            **
C    **                                                               **
C    ** ROUTINES REFERENCED                                           **
C    **                                                               **
C    ** SUBROUTINE READCN ( CNFILE )                                  **
C    **    READS IN CONFIGURATION AND BOX VARIABLES                   **
C    ** SUBROUTINE FORCE ( RCUT, V, W, X, RPX, PF )                   **
C    **    CALCULATES FORCES, POTENTIAL, VIRIAL, HYPERVIRIAL ETC.     **
C    ** SUBROUTINE KINET ( K )                                        **
C    **    CALCULATES KINETIC ENERGY                                  **
C    ** SUBROUTINE PREDIC ( DT )                                      **
C    **    PREDICTOR ROUTINE FOR CONFIGURATION AND BOX VARIABLES      **
C    ** SUBROUTINE CORREC ( DT, CHI, CHIPXI )                         **
C    **    CORRECTOR ROUTINE FOR CONFIGURATION AND BOX VARIABLES      **
C    ** SUBROUTINE WRITCN ( CNFILE )                                  **
C    **    WRITES OUT CONFIGURATION AND BOX VARIABLES                 **
C    ** SUBROUTINE SCALE ( TEMPER, PRESUR, WLRC0, XLRC0, RCUT )       **
C    **    SCALES MOMENTA AND BOX SIZE TO GIVE DESIRED T AND P        **
C    *******************************************************************

        INTEGER     N
        PARAMETER ( N = 108 )

        REAL        RX(N), RY(N), RZ(N)
        REAL        RX1(N), RY1(N), RZ1(N)
        REAL        RX2(N), RY2(N), RZ2(N)
        REAL        RX3(N), RY3(N), RZ3(N)
        REAL        PX(N), PY(N), PZ(N)
        REAL        PX1(N), PY1(N), PZ1(N)
        REAL        PX2(N), PY2(N), PZ2(N)
        REAL        PX3(N), PY3(N), PZ3(N)
        REAL        FX(N), FY(N), FZ(N)
        REAL        BOX, BOX1, BOX2, BOX3

        INTEGER     STEP, NSTEP, IPRINT, ISCALE
        REAL        ACV, ACK, ACE, ACP, ACT, ACH, ACD
        REAL        ACVSQ, ACKSQ, ACESQ, ACPSQ, ACTSQ, ACHSQ, ACDSQ
        REAL        AVV, AVK, AVE, AVP, AVT, AVH, AVD
        REAL        FLV, FLK, FLE, FLP, FLT, FLH, FLD
        REAL        DT, DENS, TEMP, RCUT, VOL, PRES, H, NORM
        REAL        TEMPER, PRESUR
        REAL        K, V, W, E
        REAL        KN, VN, EN, HN
        REAL        X, RPX, PF, PP, PV, CHI, CHIPXI
        REAL        SR3, SR9, VLRC, WLRC, XLRC, VLRC0, WLRC0, XLRC0, PI
        CHARACTER   TITLE*80, CNFILE*30
        REAL        FREE

        PARAMETER ( FREE = 3.0 )
        PARAMETER ( PI = 3.1415927 )

C    *******************************************************************

        WRITE(*,'(1H1,'' **** PROGRAM EVAMOR ****                  '')')
        WRITE(*,'(//1X,''MOLECULAR DYNAMICS OF LENNARD-JONES ATOMS '')')
        WRITE(*,'(1X,''CONSTANT-NPT ALGORITHM OF EVANS AND MORRISS '')')

C    ** BASIC SIMULATION PARAMETERS **

        WRITE(*,'('' ENTER RUN TITLE                               '')')
        READ (*,'(A)') TITLE
        WRITE(*,'('' ENTER CONFIGURATION FILENAME                  '')')
        READ (*,'(A)') CNFILE
        WRITE(*,'('' ENTER NUMBER OF STEPS                         '')')
        READ (*,*) NSTEP
        WRITE(*,'('' ENTER INTERVAL BETWEEN PRINTS                 '')')
        READ (*,*) IPRINT
        WRITE(*,'('' ENTER INTERVAL BETWEEN BOX AND MOMENTUM SCALES'')')
        READ (*,*) ISCALE
        WRITE(*,'('' ENTER THE FOLLOWING IN L-J REDUCED UNITS      '')')
        WRITE(*,'('' ENTER TIMESTEP                                '')')
        READ (*,*) DT
        WRITE(*,'('' ENTER POTENTIAL CUTOFF                        '')')
        READ (*,*) RCUT
        WRITE(*,'('' ENTER DESIRED TEMPERATURE                     '')')
        READ (*,*) TEMPER
        WRITE(*,'('' ENTER DESIRED PRESSURE                        '')')
        READ (*,*) PRESUR

        WRITE(*,'(//1X,A)') TITLE
        WRITE(*,'('' CONFIGURATION FILENAME '',A)') CNFILE
        WRITE(*,'('' NUMBER OF STEPS  = '',I6   )') NSTEP
        WRITE(*,'('' PRINT INTERVAL   = '',I6   )') IPRINT
        WRITE(*,'('' SCALE INTERVAL   = '',I6   )') ISCALE
        WRITE(*,'('' TIMESTEP         = '',F10.5)') DT
        WRITE(*,'('' POTENTIAL CUTOFF = '',F10.5)') RCUT
        WRITE(*,'('' DESIRED TEMP.    = '',F10.5)') TEMPER
        WRITE(*,'('' DESIRED PRES.    = '',F10.5)') PRESUR

C    ** READCN MUST READ IN INITIAL CONFIGURATION    **
C    ** AND ASSIGN VALUES TO BOX AND ITS DERIVATIVES **

        CALL READCN ( CNFILE )
        VOL = BOX ** 3
        DENS = REAL ( N ) / VOL

        WRITE(*,'('' INITIAL DENS.    = '',F10.5)') DENS

        IF ( IPRINT .LE. 0 ) IPRINT = NSTEP + 1
        IF ( ISCALE .LE. 0 ) ISCALE = NSTEP + 1

C    ** PREPARE FACTORS FOR LONG-RANGE CORRECTIONS **
C    ** NB: SPECIFIC TO LENNARD-JONES POTENTIAL    **

        SR3 = ( 1.0 / RCUT ) ** 3
        SR9 = SR3 ** 3
        VLRC0 =   8.0 * PI * REAL ( N ) * SR9 / 9.0
     :          - 8.0 * PI * REAL ( N ) * SR3 / 3.0
        WLRC0 =  32.0 * PI * REAL ( N ) * SR9 / 9.0
     :         - 16.0 * PI * REAL ( N ) * SR3 / 3.0
        XLRC0 = 128.0 * PI * REAL ( N ) * SR9 / 9.0
     :         - 32.0 * PI * REAL ( N ) * SR3 / 3.0

C    ** ZERO ACCUMULATORS **

        ACV = 0.0
        ACK = 0.0
        ACE = 0.0
        ACP = 0.0
        ACT = 0.0
        ACH = 0.0
        ACD = 0.0

        ACVSQ = 0.0
        ACKSQ = 0.0
        ACESQ = 0.0
        ACPSQ = 0.0
        ACTSQ = 0.0
        ACHSQ = 0.0
        ACDSQ = 0.0

        FLV = 0.0
        FLK = 0.0
        FLE = 0.0
        FLP = 0.0
        FLT = 0.0
        FLH = 0.0
        FLD = 0.0

        WRITE(*,'(//1X,''**** START OF DYNAMICS ****'')')
        WRITE(*,10001)

C    *******************************************************************
C    ** MAIN LOOP STARTS                                              **
C    *******************************************************************

        DO 1000 STEP = 1, NSTEP

C       ** IMPLEMENT ALGORITHM **

           CALL PREDIC ( DT )

           CALL FORCE ( RCUT, V, W, X, RPX, PF )
           CALL KINET ( K )

C       ** INCLUDE LONG-RANGE CORRECTIONS IN ALGORITHM **

           KN   = K / REAL ( N )
           VOL  = BOX ** 3
           DENS = REAL ( N ) / VOL
           WLRC = WLRC0 * DENS
           XLRC = XLRC0 * DENS
           TEMP = 2.0 * KN / FREE
           PRES = DENS * TEMP + ( W + WLRC ) / VOL
           PV   = PRES * VOL
           PP   = 2.0 * K

           CHI    = - RPX / 9.0 / ( X + XLRC + PV )
           CHIPXI = PF / PP

           CALL CORREC ( DT, CHI, CHIPXI )

C       ** CALCULATE INSTANTANEOUS VALUES   **
C       ** INCLUDING LONG-RANGE CORRECTIONS **

           VOL  = BOX ** 3
           DENS = REAL ( N ) / VOL
           VLRC = VLRC0 * DENS
           WLRC = WLRC0 * DENS
           XLRC = XLRC0 * DENS
           V    = V + VLRC
           W    = W + WLRC
           X    = X + XLRC
           E    = K + V
           VN   = V / REAL ( N )
           EN   = E / REAL ( N )
           TEMP = 2.0 * KN / FREE
           PRES = DENS * TEMP + W / VOL
           H    = E + PRES * VOL
           HN   = H / REAL ( N )

C       ** INCREMENT ACCUMULATORS **

           ACE = ACE + EN
           ACK = ACK + KN
           ACV = ACV + VN
           ACP = ACP + PRES
           ACH = ACH + HN
           ACD = ACD + DENS

           ACESQ = ACESQ + EN ** 2
           ACKSQ = ACKSQ + KN ** 2
           ACVSQ = ACVSQ + VN ** 2
           ACPSQ = ACPSQ + PRES ** 2
           ACHSQ = ACHSQ + HN ** 2
           ACDSQ = ACDSQ + DENS ** 2

C       ** OPTIONALLY PRINT INFORMATION **

           IF ( MOD ( STEP, IPRINT ) .EQ. 0 ) THEN

              WRITE(*,'(1X,I8,7(2X,F10.5))')
     :                 STEP, EN, HN, KN, VN, PRES, TEMP, DENS

           ENDIF

C       ** OPTIONALLY SCALE MOMENTA AND BOX SIZE **

           IF ( MOD ( STEP, ISCALE ) .EQ. 0 ) THEN

              CALL SCALE ( TEMPER, PRESUR, WLRC0, XLRC0, RCUT )

           ENDIF

1000    CONTINUE

C    *******************************************************************
C    ** MAIN LOOP ENDS                                                **
C    *******************************************************************

        WRITE(*,'(/1X,''**** END OF DYNAMICS **** ''//)')

C    ** WRITE OUT FINAL CONFIGURATION **
C    ** INCLUDING BOX,BOX1,BOX2,BOX3  **

        CALL WRITCN ( CNFILE )

C    ** WRITE OUT FINAL AVERAGES **

        NORM = REAL ( NSTEP )
        AVE  = ACE / NORM
        AVK  = ACK / NORM
        AVV  = ACV / NORM
        AVP  = ACP / NORM
        AVH  = ACH / NORM
        AVD  = ACD / NORM

        ACESQ = ( ACESQ / NORM ) - AVE ** 2
        ACKSQ = ( ACKSQ / NORM ) - AVK ** 2
        ACVSQ = ( ACVSQ / NORM ) - AVV ** 2
        ACPSQ = ( ACPSQ / NORM ) - AVP ** 2
        ACHSQ = ( ACHSQ / NORM ) - AVH ** 2
        ACDSQ = ( ACDSQ / NORM ) - AVD ** 2

        IF ( ACESQ .GT. 0.0 ) FLE = SQRT ( ACESQ )
        IF ( ACKSQ .GT. 0.0 ) FLK = SQRT ( ACKSQ )
        IF ( ACVSQ .GT. 0.0 ) FLV = SQRT ( ACVSQ )
        IF ( ACPSQ .GT. 0.0 ) FLP = SQRT ( ACPSQ )
        IF ( ACHSQ .GT. 0.0 ) FLH = SQRT ( ACHSQ )
        IF ( ACDSQ .GT. 0.0 ) FLD = SQRT ( ACDSQ )

        AVT = AVK / 1.5
        FLT = FLK / 1.5

        WRITE(*,'('' AVERAGES'',7(2X,F10.5))')
     :             AVE, AVH, AVK, AVV, AVP, AVT, AVD
        WRITE(*,'('' FLUCTS  '',7(2X,F10.5))')
     :             FLE, FLH, FLK, FLV, FLP, FLT, FLD

        STOP

10001   FORMAT(//1X,'TIMESTEP  ..ENERGY..  .ENTHALPY.  ..KINETIC.',
     :          '  ..POTENT..  .PRESSURE.  ..TEMPER..  ..DENSITY.')
        END



        SUBROUTINE FORCE ( RCUT, V, W, X, RPX, PF )

        COMMON / BLOCK1 / RX, RY, RZ, RX1, RY1, RZ1,
     :                    RX2, RY2, RZ2, RX3, RY3, RZ3,
     :                    PX, PY, PZ, PX1, PY1, PZ1,
     :                    PX2, PY2, PZ2, PX3, PY3, PZ3,
     :                    FX, FY, FZ
        COMMON / BLOCK2 / BOX, BOX1, BOX2, BOX3

C    *******************************************************************
C    ** LENNARD-JONES FORCE ROUTINE IN REDUCED UNITS                  **
C    **                                                               **
C    ** THE POTENTIAL IS V(R) = 4*((1/R)**12-(1/R)**6)                **
C    ** WE INCLUDE SPHERICAL CUTOFF AND MINIMUM IMAGING IN CUBIC BOX. **
C    **                                                               **
C    ** PRINCIPAL VARIABLES:                                          **
C    **                                                               **
C    ** INTEGER N                 NUMBER OF MOLECULES                 **
C    ** REAL    RX(N),RY(N),RZ(N) MOLECULAR POSITIONS                 **
C    ** REAL    PX(N),PY(N),PZ(N) MOLECULAR MOMENTA                   **
C    ** REAL    FX(N),FY(N),FZ(N) MOLECULAR FORCES                    **
C    ** REAL    BOX               SIMULATION BOX LENGTH               **
C    ** REAL    RCUT              PAIR POTENTIAL CUTOFF               **
C    ** REAL    V                 POTENTIAL ENERGY                    **
C    ** REAL    W                 VIRIAL FUNCTION                     **
C    ** REAL    X                 HYPERVIRIAL FUNCTION                **
C    ** REAL    RPX               ADDITIONAL PAIR SUMMATION           **
C    ** REAL    PF                ANOTHER PAIR SUMMATION              **
C    *******************************************************************

        INTEGER     N
        PARAMETER ( N = 108 )

        REAL        RX(N), RY(N), RZ(N)
        REAL        RX1(N), RY1(N), RZ1(N)
        REAL        RX2(N), RY2(N), RZ2(N)
        REAL        RX3(N), RY3(N), RZ3(N)
        REAL        PX(N), PY(N), PZ(N)
        REAL        PX1(N), PY1(N), PZ1(N)
        REAL        PX2(N), PY2(N), PZ2(N)
        REAL        PX3(N), PY3(N), PZ3(N)
        REAL        FX(N), FY(N), FZ(N)
        REAL        BOX, BOX1, BOX2, BOX3

        INTEGER     I, J
        REAL        RCUT, V, W, X, RPX, PF
        REAL        BOXINV, RCUTSQ
        REAL        RXI, RYI, RZI, RXIJ, RYIJ, RZIJ, RIJSQ
        REAL        PXI, PYI, PZI, PXIJ, PYIJ, PZIJ
        REAL        FXI, FYI, FZI, FXIJ, FYIJ, FZIJ
        REAL        SR2, SR6, SR12, VIJ, WIJ, FIJ, XIJ, RP

C    *******************************************************************

C    ** USEFUL QUANTITIES **

        BOXINV = 1.0 / BOX
        RCUTSQ = RCUT ** 2

C    ** ZERO FORCES, POTENTIAL, VIRIAL **

        DO 100 I = 1, N

           FX(I) = 0.0
           FY(I) = 0.0
           FZ(I) = 0.0

100     CONTINUE

        V   = 0.0
        W   = 0.0
        X   = 0.0
        RPX = 0.0
        PF  = 0.0

C    ** OUTER LOOP BEGINS **

        DO 200 I = 1, N - 1

           RXI = RX(I)
           RYI = RY(I)
           RZI = RZ(I)
           FXI = FX(I)
           FYI = FY(I)
           FZI = FZ(I)
           PXI = PX(I)
           PYI = PY(I)
           PZI = PZ(I)

C       ** INNER LOOP BEGINS **

           DO 199 J = I + 1, N

              RXIJ = RXI - RX(J)
              RYIJ = RYI - RY(J)
              RZIJ = RZI - RZ(J)
              RXIJ = RXIJ - ANINT ( RXIJ * BOXINV ) * BOX
              RYIJ = RYIJ - ANINT ( RYIJ * BOXINV ) * BOX
              RZIJ = RZIJ - ANINT ( RZIJ * BOXINV ) * BOX
              RIJSQ  = RXIJ ** 2 + RYIJ ** 2 + RZIJ ** 2

              IF ( RIJSQ .LT. RCUTSQ ) THEN

                 SR2   = 1.0 / RIJSQ
                 SR6   = SR2 * SR2 * SR2
                 SR12  = SR6 ** 2
                 VIJ   = SR12 - SR6
                 V     = V + VIJ
                 WIJ   = VIJ + SR12
                 W     = W + WIJ
                 FIJ   = WIJ * SR2
                 FXIJ  = FIJ * RXIJ
                 FYIJ  = FIJ * RYIJ
                 FZIJ  = FIJ * RZIJ
                 FXI   = FXI + FXIJ
                 FYI   = FYI + FYIJ
                 FZI   = FZI + FZIJ
                 FX(J) = FX(J) - FXIJ
                 FY(J) = FY(J) - FYIJ
                 FZ(J) = FZ(J) - FZIJ
                 XIJ   = WIJ + 2.0 * SR12
                 X     = X + XIJ

                 PXIJ  = PXI - PX(J)
                 PYIJ  = PYI - PY(J)
                 PZIJ  = PZI - PZ(J)
                 RP    = RXIJ * PXIJ + RYIJ * PYIJ + RZIJ * PZIJ
                 RPX   = RPX + RP * XIJ * SR2
                 PF    = PF + PXIJ * FXIJ + PYIJ * FYIJ + PZIJ * FZIJ

              ENDIF

199        CONTINUE

C       ** INNER LOOP ENDS **

           FX(I) = FXI
           FY(I) = FYI
           FZ(I) = FZI

200     CONTINUE

C    ** OUTER LOOP ENDS **

C    ** MULTIPLY RESULTS BY NUMERICAL FACTORS **

        DO 300 I = 1, N

           FX(I) = FX(I) * 24.0
           FY(I) = FY(I) * 24.0
           FZ(I) = FZ(I) * 24.0

300     CONTINUE

        V   = V * 4.0
        W   = W * 24.0 / 3.0
        X   = X * 144.0 / 9.0
        RPX = RPX * 144.0
        PF  = PF * 24.0

        RETURN
        END



        SUBROUTINE KINET ( K )

        COMMON / BLOCK1 / RX, RY, RZ, RX1, RY1, RZ1,
     :                    RX2, RY2, RZ2, RX3, RY3, RZ3,
     :                    PX, PY, PZ, PX1, PY1, PZ1,
     :                    PX2, PY2, PZ2, PX3, PY3, PZ3,
     :                    FX, FY, FZ
        COMMON / BLOCK2 / BOX, BOX1, BOX2, BOX3

C    *******************************************************************
C    ** ROUTINE TO COMPUTE KINETIC ENERGY                             **
C    *******************************************************************

        INTEGER     N
        PARAMETER ( N = 108 )

        REAL        RX(N), RY(N), RZ(N)
        REAL        RX1(N), RY1(N), RZ1(N)
        REAL        RX2(N), RY2(N), RZ2(N)
        REAL        RX3(N), RY3(N), RZ3(N)
        REAL        PX(N), PY(N), PZ(N)
        REAL        PX1(N), PY1(N), PZ1(N)
        REAL        PX2(N), PY2(N), PZ2(N)
        REAL        PX3(N), PY3(N), PZ3(N)
        REAL        FX(N), FY(N), FZ(N)
        REAL        BOX, BOX1, BOX2, BOX3

        REAL        K
        INTEGER     I

C    *******************************************************************

        K = 0.0

        DO 1000 I = 1, N

           K = K + PX(I) ** 2 + PY(I) ** 2 + PZ(I) ** 2

1000    CONTINUE

        K = 0.5 * K

        RETURN
        END



        SUBROUTINE READCN ( CNFILE )

        COMMON / BLOCK1 / RX, RY, RZ, RX1, RY1, RZ1,
     :                    RX2, RY2, RZ2, RX3, RY3, RZ3,
     :                    PX, PY, PZ, PX1, PY1, PZ1,
     :                    PX2, PY2, PZ2, PX3, PY3, PZ3,
     :                    FX, FY, FZ
        COMMON / BLOCK2 / BOX, BOX1, BOX2, BOX3

C    *******************************************************************
C    ** SUBROUTINE TO READ IN INITIAL CONFIGURATION FROM UNIT 10      **
C    *******************************************************************

        INTEGER     N
        PARAMETER ( N = 108 )

        REAL        RX(N), RY(N), RZ(N)
        REAL        RX1(N), RY1(N), RZ1(N)
        REAL        RX2(N), RY2(N), RZ2(N)
        REAL        RX3(N), RY3(N), RZ3(N)
        REAL        PX(N), PY(N), PZ(N)
        REAL        PX1(N), PY1(N), PZ1(N)
        REAL        PX2(N), PY2(N), PZ2(N)
        REAL        PX3(N), PY3(N), PZ3(N)
        REAL        FX(N), FY(N), FZ(N)
        REAL        BOX, BOX1, BOX2, BOX3

        CHARACTER   CNFILE*(*)

        INTEGER     CNUNIT, NN
        PARAMETER ( CNUNIT = 10 )

C     ******************************************************************

        OPEN ( UNIT = CNUNIT, FILE = CNFILE,
     :         STATUS = 'OLD', FORM = 'UNFORMATTED' )

        READ ( CNUNIT ) NN, BOX, BOX1, BOX2, BOX3
        IF ( NN .NE. N ) STOP 'INCORRECT VALUE OF N'
        READ ( CNUNIT ) RX, RY, RZ
        READ ( CNUNIT ) RX1, RY1, RZ1
        READ ( CNUNIT ) RX2, RY2, RZ2
        READ ( CNUNIT ) RX3, RY3, RZ3
        READ ( CNUNIT ) PX, PY, PZ
        READ ( CNUNIT ) PX1, PY1, PZ1
        READ ( CNUNIT ) PX2, PY2, PZ2
        READ ( CNUNIT ) PX3, PY3, PZ3

        CLOSE ( UNIT = CNUNIT )

        RETURN
        END



        SUBROUTINE WRITCN ( CNFILE )

        COMMON / BLOCK1 / RX, RY, RZ, RX1, RY1, RZ1,
     :                    RX2, RY2, RZ2, RX3, RY3, RZ3,
     :                    PX, PY, PZ, PX1, PY1, PZ1,
     :                    PX2, PY2, PZ2, PX3, PY3, PZ3,
     :                    FX, FY, FZ
        COMMON / BLOCK2 / BOX, BOX1, BOX2, BOX3

C    *******************************************************************
C    ** ROUTINE TO WRITE OUT FINAL CONFIGURATION TO UNIT 10           **
C    *******************************************************************

        INTEGER     N
        PARAMETER ( N = 108 )

        REAL        RX(N), RY(N), RZ(N)
        REAL        RX1(N), RY1(N), RZ1(N)
        REAL        RX2(N), RY2(N), RZ2(N)
        REAL        RX3(N), RY3(N), RZ3(N)
        REAL        PX(N), PY(N), PZ(N)
        REAL        PX1(N), PY1(N), PZ1(N)
        REAL        PX2(N), PY2(N), PZ2(N)
        REAL        PX3(N), PY3(N), PZ3(N)
        REAL        FX(N), FY(N), FZ(N)
        REAL        BOX, BOX1, BOX2, BOX3

        CHARACTER   CNFILE*(*)

        INTEGER     CNUNIT
        PARAMETER ( CNUNIT = 10 )

C    *******************************************************************

        OPEN ( UNIT = CNUNIT, FILE = CNFILE,
     :         STATUS = 'OLD', FORM = 'UNFORMATTED' )

        WRITE ( CNUNIT ) N, BOX, BOX1, BOX2, BOX3
        WRITE ( CNUNIT ) RX, RY, RZ
        WRITE ( CNUNIT ) RX1, RY1, RZ1
        WRITE ( CNUNIT ) RX2, RY2, RZ2
        WRITE ( CNUNIT ) RX3, RY3, RZ3
        WRITE ( CNUNIT ) PX, PY, PZ
        WRITE ( CNUNIT ) PX1, PY1, PZ1
        WRITE ( CNUNIT ) PX2, PY2, PZ2
        WRITE ( CNUNIT ) PX3, PY3, PZ3

        CLOSE ( UNIT = CNUNIT )

        RETURN
        END



        SUBROUTINE PREDIC ( DT )

        COMMON / BLOCK1 / RX, RY, RZ, RX1, RY1, RZ1,
     :                    RX2, RY2, RZ2, RX3, RY3, RZ3,
     :                    PX, PY, PZ, PX1, PY1, PZ1,
     :                    PX2, PY2, PZ2, PX3, PY3, PZ3,
     :                    FX, FY, FZ
        COMMON / BLOCK2 / BOX, BOX1, BOX2, BOX3

C    *******************************************************************
C    ** STANDARD TAYLOR SERIES PREDICTORS                             **
C    *******************************************************************

        INTEGER     N
        PARAMETER ( N = 108 )

        REAL        RX(N), RY(N), RZ(N)
        REAL        RX1(N), RY1(N), RZ1(N)
        REAL        RX2(N), RY2(N), RZ2(N)
        REAL        RX3(N), RY3(N), RZ3(N)
        REAL        PX(N), PY(N), PZ(N)
        REAL        PX1(N), PY1(N), PZ1(N)
        REAL        PX2(N), PY2(N), PZ2(N)
        REAL        PX3(N), PY3(N), PZ3(N)
        REAL        FX(N), FY(N), FZ(N)
        REAL        BOX, BOX1, BOX2, BOX3
        REAL        DT

        INTEGER     I
        REAL        C1, C2, C3

C    *******************************************************************

        C1 = DT
        C2 = C1 * DT / 2.0
        C3 = C2 * DT / 3.0

        DO 100 I = 1, N

           RX(I)  = RX(I)  + C1*RX1(I) + C2*RX2(I) + C3*RX3(I)
           RY(I)  = RY(I)  + C1*RY1(I) + C2*RY2(I) + C3*RY3(I)
           RZ(I)  = RZ(I)  + C1*RZ1(I) + C2*RZ2(I) + C3*RZ3(I)
           RX1(I) = RX1(I) + C1*RX2(I) + C2*RX3(I)
           RY1(I) = RY1(I) + C1*RY2(I) + C2*RY3(I)
           RZ1(I) = RZ1(I) + C1*RZ2(I) + C2*RZ3(I)
           RX2(I) = RX2(I) + C1*RX3(I)
           RY2(I) = RY2(I) + C1*RY3(I)
           RZ2(I) = RZ2(I) + C1*RZ3(I)

           PX(I)  = PX(I)  + C1*PX1(I) + C2*PX2(I) + C3*PX3(I)
           PY(I)  = PY(I)  + C1*PY1(I) + C2*PY2(I) + C3*PY3(I)
           PZ(I)  = PZ(I)  + C1*PZ1(I) + C2*PZ2(I) + C3*PZ3(I)
           PX1(I) = PX1(I) + C1*PX2(I) + C2*PX3(I)
           PY1(I) = PY1(I) + C1*PY2(I) + C2*PY3(I)
           PZ1(I) = PZ1(I) + C1*PZ2(I) + C2*PZ3(I)
           PX2(I) = PX2(I) + C1*PX3(I)
           PY2(I) = PY2(I) + C1*PY3(I)
           PZ2(I) = PZ2(I) + C1*PZ3(I)

100     CONTINUE

        BOX  = BOX  + C1*BOX1 + C2*BOX2 + C3*BOX3
        BOX1 = BOX1 + C1*BOX2 + C2*BOX3
        BOX2 = BOX2 + C1*BOX3

        RETURN
        END



        SUBROUTINE CORREC ( DT, CHI, CHIPXI )

        COMMON / BLOCK1 / RX, RY, RZ, RX1, RY1, RZ1,
     :                    RX2, RY2, RZ2, RX3, RY3, RZ3,
     :                    PX, PY, PZ, PX1, PY1, PZ1,
     :                    PX2, PY2, PZ2, PX3, PY3, PZ3,
     :                    FX, FY, FZ
        COMMON / BLOCK2 / BOX, BOX1, BOX2, BOX3

C    *******************************************************************
C    ** GEAR CORRECTOR ALGORITHM.                                     **
C    **                                                               **
C    ** FOR TIMESTEP-SCALED VARIABLES GEAR COEFFICIENTS WOULD BE AS   **
C    ** FOLLOWS (4-VALUE METHOD, 1ST-ORDER D.E.): 3/8, 1, 3/4, 1/6.   **
C    ** CHIPXI IS SHORT FOR ( CHI + XI ) (SEE CHAPTER 7).             **
C    *******************************************************************

        INTEGER     N
        PARAMETER ( N = 108 )

        REAL        RX(N), RY(N), RZ(N)
        REAL        RX1(N), RY1(N), RZ1(N)
        REAL        RX2(N), RY2(N), RZ2(N)
        REAL        RX3(N), RY3(N), RZ3(N)
        REAL        PX(N), PY(N), PZ(N)
        REAL        PX1(N), PY1(N), PZ1(N)
        REAL        PX2(N), PY2(N), PZ2(N)
        REAL        PX3(N), PY3(N), PZ3(N)
        REAL        FX(N), FY(N), FZ(N)
        REAL        BOX, BOX1, BOX2, BOX3
        REAL        DT, CHI, CHIPXI

        INTEGER     I
        REAL        C1, C2, C3, COEFF0, COEFF2, COEFF3
        REAL        CORR, CORRX, CORRY, CORRZ, CORPX, CORPY, CORPZ
        REAL        RX1I, RY1I, RZ1I, PX1I, PY1I, PZ1I

        REAL        GEAR0, GEAR2, GEAR3
        PARAMETER ( GEAR0 = 3.0 / 8.0,
     :              GEAR2 = 3.0 / 4.0,
     :              GEAR3 = 1.0 / 6.0 )

C    *******************************************************************

        C1 = DT
        C2 = C1 * DT / 2.0
        C3 = C2 * DT / 3.0

        COEFF0 = GEAR0 * C1
        COEFF2 = GEAR2 * C1 / C2
        COEFF3 = GEAR3 * C1 / C3

        DO 400 I = 1, N

           RX1I = PX(I) + CHI * RX(I)
           RY1I = PY(I) + CHI * RY(I)
           RZ1I = PZ(I) + CHI * RZ(I)
           CORRX = RX1I - RX1(I)
           CORRY = RY1I - RY1(I)
           CORRZ = RZ1I - RZ1(I)

           RX(I)  = RX(I)  + COEFF0 * CORRX
           RY(I)  = RY(I)  + COEFF0 * CORRY
           RZ(I)  = RZ(I)  + COEFF0 * CORRZ
           RX1(I) = RX1I
           RY1(I) = RY1I
           RZ1(I) = RZ1I
           RX2(I) = RX2(I) + COEFF2 * CORRX
           RY2(I) = RY2(I) + COEFF2 * CORRY
           RZ2(I) = RZ2(I) + COEFF2 * CORRZ
           RX3(I) = RX3(I) + COEFF3 * CORRX
           RY3(I) = RY3(I) + COEFF3 * CORRY
           RZ3(I) = RZ3(I) + COEFF3 * CORRZ

           PX1I = FX(I) - CHIPXI * PX(I)
           PY1I = FY(I) - CHIPXI * PY(I)
           PZ1I = FZ(I) - CHIPXI * PZ(I)
           CORPX = PX1I - PX1(I)
           CORPY = PY1I - PY1(I)
           CORPZ = PZ1I - PZ1(I)

           PX(I)  = PX(I)  + COEFF0 * CORPX
           PY(I)  = PY(I)  + COEFF0 * CORPY
           PZ(I)  = PZ(I)  + COEFF0 * CORPZ
           PX1(I) = PX1I
           PY1(I) = PY1I
           PZ1(I) = PZ1I
           PX2(I) = PX2(I) + COEFF2 * CORPX
           PY2(I) = PY2(I) + COEFF2 * CORPY
           PZ2(I) = PZ2(I) + COEFF2 * CORPZ
           PX3(I) = PX3(I) + COEFF3 * CORPX
           PY3(I) = PY3(I) + COEFF3 * CORPY
           PZ3(I) = PZ3(I) + COEFF3 * CORPZ

400     CONTINUE

        CORR = CHI * BOX - BOX1
        BOX  = BOX  + COEFF0 * CORR
        BOX1 = CHI * BOX
        BOX2 = BOX2 + COEFF2 * CORR
        BOX3 = BOX3 + COEFF3 * CORR

        RETURN
        END



        SUBROUTINE SCALE ( TEMPER, PRESUR, WLRC0, XLRC0, RCUT )

        COMMON / BLOCK1 / RX, RY, RZ, RX1, RY1, RZ1,
     :                    RX2, RY2, RZ2, RX3, RY3, RZ3,
     :                    PX, PY, PZ, PX1, PY1, PZ1,
     :                    PX2, PY2, PZ2, PX3, PY3, PZ3,
     :                    FX, FY, FZ
        COMMON / BLOCK2 / BOX, BOX1, BOX2, BOX3

C    *******************************************************************
C    ** SCALES MOMENTA AND BOX SIZE TO GIVE DESIRED VALUES OF T AND P.**
C    **                                                               **
C    ** WE USE DIRECT MOMENTUM SCALING TO GIVE THE TEMPERATURE AND A  **
C    ** NEWTON-RAPHSON METHOD FOR THE BOX SIZE.                       **
C    ** WE USE THE PRESSURE DERIVATIVE FUNCTION                       **
C    ** BOX * DP/D(BOX) = 3 * VOL * DP/D(VOL) = 3 * ( - P - X / VOL ) **
C    ** WHERE P IS THE PRESSURE AND X THE HYPERVIRIAL FUNCTION.       **
C    ** LONG-RANGE CORRECTIONS ARE TAKEN INTO ACCOUNT.                **
C    *******************************************************************

        INTEGER     N
        PARAMETER ( N = 108 )

        REAL        RX(N), RY(N), RZ(N)
        REAL        RX1(N), RY1(N), RZ1(N)
        REAL        RX2(N), RY2(N), RZ2(N)
        REAL        RX3(N), RY3(N), RZ3(N)
        REAL        PX(N), PY(N), PZ(N)
        REAL        PX1(N), PY1(N), PZ1(N)
        REAL        PX2(N), PY2(N), PZ2(N)
        REAL        PX3(N), PY3(N), PZ3(N)
        REAL        FX(N), FY(N), FZ(N)
        REAL        BOX, BOX1, BOX2, BOX3

        INTEGER     I
        REAL        TEMPER, PRESUR, WLRC0, XLRC0, RCUT
        REAL        K, KN, V, W, X, RPX, PF, FACTOR
        REAL        VOL, DENS, WLRC, XLRC, TEMP, PRES
        REAL        FREE, TOL
        PARAMETER ( FREE = 3.0, TOL = 0.01 )

C    *******************************************************************

C    ** SCALE MOMENTA **

        CALL KINET ( K )
        KN = K / REAL ( N )
        TEMP = 2.0 * KN / FREE
        FACTOR = SQRT ( TEMPER / TEMP )

        DO 100 I = 1, N

           PX(I) = PX(I) * FACTOR
           PY(I) = PY(I) * FACTOR
           PZ(I) = PZ(I) * FACTOR

100     CONTINUE

        TEMP = TEMPER

C    ** SCALE PRESSURE USING NEWTON-RAPHSON PROCEDURE **

        CALL FORCE ( RCUT, V, W, X, RPX, PF )
        VOL  = BOX ** 3
        DENS = REAL ( N ) / VOL
        WLRC = WLRC0 * DENS
        XLRC = XLRC0 * DENS
        W    = W + WLRC
        X    = X + XLRC
        PRES = DENS * TEMP + W / VOL

1000    IF ( ABS ( PRES - PRESUR ) .GT. TOL ) THEN

           FACTOR = 1.0 + ( PRES - PRESUR ) / ( PRES + X / VOL ) / 3.0

           DO 200 I = 1, N

              RX(I) = RX(I) * FACTOR
              RY(I) = RY(I) * FACTOR
              RZ(I) = RZ(I) * FACTOR

200        CONTINUE

           BOX = BOX * FACTOR

           CALL FORCE ( RCUT, V, W, X, RPX, PF )
           VOL  = BOX ** 3
           DENS = REAL ( N ) / VOL
           WLRC = WLRC0 * DENS
           XLRC = XLRC0 * DENS
           W    = W + WLRC
           X    = X + XLRC
           PRES = DENS * TEMP + W / VOL

           GOTO 1000

        ENDIF

        RETURN
        END



Modified: Sat Jul 22 04:41:13 2000 GMT
Page accessed 11517 times since Sat Apr 17 21:34:20 1999 GMT