MoDeNa  1.0
Software framework facilitating sequential multi-scale modelling
Spline_Integration_d.F90
1 
4 
5 
6 
7 
8 
9 
10 
11 
12 
13 
14 
15 ! Generated by TAPENADE (INRIA, Tropics team)
16 ! Tapenade 3.10 (r5498) - 20 Jan 2015 09:48
17 !
18 ! Differentiation of spline in forward (tangent) mode:
19 ! variations of useful results: y2
20 ! with respect to varying inputs: y2 y
21 !WWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWW
22 ! SUBROUTINE spline
23 !
24 ! Given arrays x(1:n) and y(1:n) containing a tabulated function,
25 ! i.e., yi = f(xi), with x1 < x2 < .. . < xN, and given values yp1 and
26 ! ypn for the first derivative of the interpolating function at points 1
27 ! and n, respectively, this routine returns an array y2(1:n) of length n
28 ! which contains the second derivatives of the interpolating function at
29 ! the tabulated points xi. If yp1 and/or ypn are equal to 1 1030 or
30 ! larger, the routine is signaled to set the corresponding boundary
31 ! condition for a natural spline, with zero second derivative on that
32 ! boundary.
33 ! Parameter: NMAX is the largest anticipated value of n.
34 !WWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWW
35 !
36 SUBROUTINE spline_d(x, y, yd, n, yp1, ypn, y2, y2d)
37  IMPLICIT NONE
38 !
39 ! ----------------------------------------------------------------------
40  INTEGER, INTENT(IN) :: n
41  REAL, INTENT(IN) :: x(n)
42  REAL, INTENT(IN) :: y(n)
43  REAL, INTENT(IN) :: yd(n)
44  REAL, INTENT(IN) :: yp1
45  REAL, INTENT(IN) :: ypn
46  REAL, INTENT(OUT) :: y2(n)
47  REAL, INTENT(OUT) :: y2d(n)
48 !
49 ! ----------------------------------------------------------------------
50  INTEGER, PARAMETER :: nmax=1000
51  INTEGER :: i, k
52  REAL :: p, qn, sig, un, u(nmax)
53  REAL :: pd, und, ud(nmax)
54 ! ----------------------------------------------------------------------
55  IF (yp1 .GT. 0.99e30) THEN
56  y2d(1) = 0.0
57  y2(1) = 0.0
58  u(1) = 0.0
59  ud = 0.0
60  ELSE
61  y2d(1) = 0.0
62  y2(1) = -0.5
63  ud = 0.0
64  ud(1) = 3.0*(yd(2)-yd(1))/(x(2)-x(1))**2
65  u(1) = 3.0/(x(2)-x(1))*((y(2)-y(1))/(x(2)-x(1))-yp1)
66  END IF
67  DO i=2,n-1
68  IF ((x(i+1) - x(i) .EQ. 0.0 .OR. x(i) - x(i-1) .EQ. 0.0) .OR. x(i+1)&
69 & - x(i-1) .EQ. 0.0) THEN
70  GOTO 100
71  ELSE
72  sig = (x(i)-x(i-1))/(x(i+1)-x(i-1))
73  pd = sig*y2d(i-1)
74  p = sig*y2(i-1) + 2.0
75  y2d(i) = -((sig-1.0)*pd/p**2)
76  y2(i) = (sig-1.0)/p
77  ud(i) = ((6.0*((yd(i+1)-yd(i))/(x(i+1)-x(i))-(yd(i)-yd(i-1))/(x(i)&
78 & -x(i-1)))/(x(i+1)-x(i-1))-sig*ud(i-1))*p-(6.0*((y(i+1)-y(i))/(x(&
79 & i+1)-x(i))-(y(i)-y(i-1))/(x(i)-x(i-1)))/(x(i+1)-x(i-1))-sig*u(i-&
80 & 1))*pd)/p**2
81  u(i) = (6.0*((y(i+1)-y(i))/(x(i+1)-x(i))-(y(i)-y(i-1))/(x(i)-x(i-1&
82 & )))/(x(i+1)-x(i-1))-sig*u(i-1))/p
83  END IF
84  END DO
85  IF (ypn .GT. 0.99e30) THEN
86  qn = 0.0
87  un = 0.0
88  und = 0.0
89  ELSE
90  qn = 0.5
91  und = -(3.0*(yd(n)-yd(n-1))/(x(n)-x(n-1))**2)
92  un = 3.0/(x(n)-x(n-1))*(ypn-(y(n)-y(n-1))/(x(n)-x(n-1)))
93  END IF
94  y2d(n) = ((und-qn*ud(n-1))*(qn*y2(n-1)+1.0)-(un-qn*u(n-1))*qn*y2d(n-1)&
95 & )/(qn*y2(n-1)+1.0)**2
96  y2(n) = (un-qn*u(n-1))/(qn*y2(n-1)+1.0)
97  DO k=n-1,1,-1
98  y2d(k) = y2d(k)*y2(k+1) + y2(k)*y2d(k+1) + ud(k)
99  y2(k) = y2(k)*y2(k+1) + u(k)
100  END DO
101  GOTO 110
102  100 WRITE(*, *) 'i x', i, x(i+1), x(i), x(i-1)
103  WRITE(*, *) 'error in spline-interpolation'
104  stop
105  110 CONTINUE
106 END SUBROUTINE spline_d
107 
108 
109 
110 
111 
112 
113 ! Generated by TAPENADE (INRIA, Tropics team)
114 ! Tapenade 3.10 (r5498) - 20 Jan 2015 09:48
115 !
116 ! Differentiation of splint_integral in forward (tangent) mode:
117 ! variations of useful results: integral
118 ! with respect to varying inputs: y2a ya
119 !WWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWW
120 ! SUBROUTINE splint_integral
121 !
122 ! Given the arrays xa(1:n) and ya(1:n) of length n, which tabulate a
123 ! function (with the in order), and given the array y2a(1:n), which is
124 ! the output from spline above, and given a value of x, this routine
125 ! returns a cubic-spline interpolated value y.
126 !WWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWW
127 !
128 SUBROUTINE splint_integral_d(xa, ya, yad, y2a, y2ad, n, xlo, xhi, &
129 & integral, integrald)
130  IMPLICIT NONE
131 ! the -1 in (khi_L-1) because khi_L was already counted up
132 !
133 ! ----------------------------------------------------------------------
134  INTEGER, INTENT(IN) :: n
135  REAL, INTENT(IN) :: xa(n)
136  REAL, INTENT(IN) :: ya(n)
137  REAL, INTENT(IN) :: yad(n)
138  REAL, INTENT(IN) :: y2a(n)
139  REAL, INTENT(IN) :: y2ad(n)
140  REAL, INTENT(IN) :: xlo
141  REAL, INTENT(IN) :: xhi
142  REAL, INTENT(OUT) :: integral
143  REAL, INTENT(OUT) :: integrald
144 !
145 ! ----------------------------------------------------------------------
146  INTEGER :: k, khi_l, klo_l, khi_h, klo_h
147  REAL :: xl, xh, h, int, x0, x1, y0, y1, y20, y21
148  REAL :: intd, y0d, y1d, y20d, y21d
149 ! ----------------------------------------------------------------------
150  integral = 0.0
151  klo_l = 1
152  khi_l = n
153  1 IF (khi_l - klo_l .GT. 1) THEN
154  k = (khi_l+klo_l)/2
155  IF (xa(k) .GT. xlo) THEN
156  khi_l = k
157  ELSE
158  klo_l = k
159  END IF
160  GOTO 1
161  END IF
162  klo_h = 1
163  khi_h = n
164  2 IF (khi_h - klo_h .GT. 1) THEN
165  k = (khi_h+klo_h)/2
166  IF (xa(k) .GT. xhi) THEN
167  khi_h = k
168  ELSE
169  klo_h = k
170  END IF
171  GOTO 2
172  END IF
173 ! integration in spline pieces, the lower interval, bracketed
174 ! by xa(klo_L) and xa(khi_L) is in steps shifted upward.
175 ! first: determine upper integration bound
176  xl = xlo
177  integrald = 0.0
178  3 IF (khi_h .GT. khi_l) THEN
179  xh = xa(khi_l)
180  ELSE IF (khi_h .EQ. khi_l) THEN
181  xh = xhi
182  ELSE
183  WRITE(*, *) 'error in spline-integration'
184  pause
185  END IF
186  h = xa(khi_l) - xa(klo_l)
187  IF (h .EQ. 0.0) pause'bad xa input in splint'
188  x0 = xa(klo_l)
189  x1 = xa(khi_l)
190  y0d = yad(klo_l)
191  y0 = ya(klo_l)
192  y1d = yad(khi_l)
193  y1 = ya(khi_l)
194  y20d = y2ad(klo_l)
195  y20 = y2a(klo_l)
196  y21d = y2ad(khi_l)
197  y21 = y2a(khi_l)
198 ! int = -xL/h * ( (x1-.5*xL)*y0 + (0.5*xL-x0)*y1 &
199 ! +y20/6.*(x1**3-1.5*xL*x1*x1+xL*xL*x1-.25*xL**3) &
200 ! -y20/6.*h*h*(x1-.5*xL) &
201 ! +y21/6.*(.25*xL**3-xL*xL*x0+1.5*xL*x0*x0-x0**3) &
202 ! -y21/6.*h*h*(.5*xL-x0) )
203 ! int = int + xH/h * ( (x1-.5*xH)*y0 + (0.5*xH-x0)*y1 &
204 ! +y20/6.*(x1**3-1.5*xH*x1*x1+xH*xH*x1-.25*xH**3) &
205 ! -y20/6.*h*h*(x1-.5*xH) &
206 ! +y21/6.*(.25*xH**3-xH*xH*x0+1.5*xH*x0*x0-x0**3) &
207 ! -y21/6.*h*h*(.5*xH-x0) )
208  intd = -((xl*((x1-.5*xl)*y0d+(0.5*xl-x0)*y1d)-(x1-xl)**4*y20d/24.+(0.5&
209 & *xl*xl-x1*xl)*h**2*y20d/6.+(xl-x0)**4*y21d/24.-(0.5*xl*xl-x0*xl)*h**&
210 & 2*y21d/6.)/h)
211  int = -(1.0/h*(xl*((x1-.5*xl)*y0+(0.5*xl-x0)*y1)-y20/24.*(x1-xl)**4+&
212 & y20/6.*(0.5*xl*xl-x1*xl)*h*h+y21/24.*(xl-x0)**4-y21/6.*(0.5*xl*xl-x0&
213 & *xl)*h*h))
214  intd = intd + (xh*((x1-.5*xh)*y0d+(0.5*xh-x0)*y1d)-(x1-xh)**4*y20d/24.&
215 & +(0.5*xh*xh-x1*xh)*h**2*y20d/6.+(xh-x0)**4*y21d/24.-(0.5*xh*xh-x0*xh&
216 & )*h**2*y21d/6.)/h
217  int = int + 1.0/h*(xh*((x1-.5*xh)*y0+(0.5*xh-x0)*y1)-y20/24.*(x1-xh)**&
218 & 4+y20/6.*(0.5*xh*xh-x1*xh)*h*h+y21/24.*(xh-x0)**4-y21/6.*(0.5*xh*xh-&
219 & x0*xh)*h*h)
220  integrald = integrald + intd
221  integral = integral + int
222 ! write (*,*) integral,x1,xH
223  klo_l = klo_l + 1
224  khi_l = khi_l + 1
225  xl = x1
226  IF (khi_h .NE. khi_l - 1) GOTO 3
227 END SUBROUTINE splint_integral_d
228 
229 
230 
double sig
correlated to variance of initial distribution