-
Notifications
You must be signed in to change notification settings - Fork 4
/
Copy pathzbrent.f
66 lines (66 loc) · 1.4 KB
/
zbrent.f
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
FUNCTION ZBRENT(FUNC,X1,X2,TOL)
PARAMETER (ITMAX=100,EPS=3.E-8)
A=X1
B=X2
FA=FUNC(A)
FB=FUNC(B)
IF(FB*FA.GT.0.) PAUSE 'Root must be bracketed for ZBRENT.'
FC=FB
DO 11 ITER=1,ITMAX
IF(FB*FC.GT.0.) THEN
C=A
FC=FA
D=B-A
E=D
ENDIF
IF(ABS(FC).LT.ABS(FB)) THEN
A=B
B=C
C=A
FA=FB
FB=FC
FC=FA
ENDIF
TOL1=2.*EPS*ABS(B)+0.5*TOL
XM=.5*(C-B)
IF(ABS(XM).LE.TOL1 .OR. FB.EQ.0.)THEN
ZBRENT=B
RETURN
ENDIF
IF(ABS(E).GE.TOL1 .AND. ABS(FA).GT.ABS(FB)) THEN
S=FB/FA
IF(A.EQ.C) THEN
P=2.*XM*S
Q=1.-S
ELSE
Q=FA/FC
R=FB/FC
P=S*(2.*XM*Q*(Q-R)-(B-A)*(R-1.))
Q=(Q-1.)*(R-1.)*(S-1.)
ENDIF
IF(P.GT.0.) Q=-Q
P=ABS(P)
IF(2.*P .LT. MIN(3.*XM*Q-ABS(TOL1*Q),ABS(E*Q))) THEN
E=D
D=P/Q
ELSE
D=XM
E=D
ENDIF
ELSE
D=XM
E=D
ENDIF
A=B
FA=FB
IF(ABS(D) .GT. TOL1) THEN
B=B+D
ELSE
B=B+SIGN(TOL1,XM)
ENDIF
FB=FUNC(B)
11 CONTINUE
PAUSE 'ZBRENT exceeding maximum iterations.'
ZBRENT=B
RETURN
END