source: Sophya/trunk/SophyaExt/CodeMinuit/code/mnderi.F@ 3359

Last change on this file since 3359 was 2403, checked in by cmv, 22 years ago

Creation du module de code source de MINUIT (CERNLIB) extrait par CMV

cmv 11/06/2003

File size: 4.8 KB
Line 
1*
2* $Id: mnderi.F,v 1.1.1.1 2003-06-11 14:18:26 cmv Exp $
3*
4* $Log: not supported by cvs2svn $
5* Revision 1.2 1996/03/15 18:02:43 james
6* Modified Files:
7* mnderi.F eliminate possible division by zero
8* mnexcm.F suppress print on STOP when print flag=-1
9* set FVAL3 to flag if FCN already called with IFLAG=3
10* mninit.F set version 96.03
11* mnlims.F remove arguments, not needed
12* mnmigr.F VLEN -> LENV in debug print statement
13* mnparm.F move call to MNRSET to after NPAR redefined, to zero all
14* mnpsdf.F eliminate possible division by zero
15* mnscan.F suppress printout when print flag =-1
16* mnset.F remove arguments in call to MNLIMS
17* mnsimp.F fix CSTATU so status is PROGRESS only if new minimum
18* mnvert.F eliminate possible division by zero
19*
20* Revision 1.1.1.1 1996/03/07 14:31:29 mclareni
21* Minuit
22*
23*
24#include "minuit/pilot.h"
25 SUBROUTINE MNDERI(FCN,FUTIL)
26#include "minuit/d506dp.inc"
27CC Calculates the first derivatives of FCN (GRD),
28CC either by finite differences or by transforming the user-
29CC supplied derivatives to internal coordinates,
30CC according to whether ISW(3) is zero or one.
31CC
32#include "minuit/d506cm.inc"
33 EXTERNAL FCN,FUTIL
34 LOGICAL LDEBUG
35 CHARACTER CBF1*22
36 NPARX = NPAR
37 LDEBUG = (IDBG(2) .GE. 1)
38 IF (AMIN .EQ. UNDEFI) CALL MNAMIN(FCN,FUTIL)
39 IF (ISW(3) .EQ. 1) GO TO 100
40 IF (LDEBUG) THEN
41C make sure starting at the right place
42 CALL MNINEX(X)
43 NPARX = NPAR
44 CALL FCN(NPARX,GIN,FS1,U,4,FUTIL)
45 NFCN = NFCN + 1
46 IF (FS1 .NE. AMIN) THEN
47 DF = AMIN - FS1
48 WRITE (CBF1(1:12),'(G12.3)') DF
49 CALL MNWARN('D','MNDERI',
50 + 'function value differs from AMIN by '//CBF1(1:12) )
51 AMIN = FS1
52 ENDIF
53 WRITE
54 + (ISYSWR,'(/'' FIRST DERIVATIVE DEBUG PRINTOUT. MNDERI''/
55 + '' PAR DERIV STEP MINSTEP OPTSTEP '',
56 + '' D1-D2 2ND DRV'')')
57 ENDIF
58 DFMIN = 8. * EPSMA2*(ABS(AMIN)+UP)
59 VRYSML = 8.* EPSMAC**2
60 IF (ISTRAT .LE. 0) THEN
61 NCYC = 2
62 TLRSTP = 0.5
63 TLRGRD = 0.1
64 ELSE IF (ISTRAT .EQ. 1) THEN
65 NCYC = 3
66 TLRSTP = 0.3
67 TLRGRD = 0.05
68 ELSE
69 NCYC = 5
70 TLRSTP = 0.1
71 TLRGRD = 0.02
72 ENDIF
73C loop over variable parameters
74 DO 60 I=1,NPAR
75 EPSPRI = EPSMA2 + ABS(GRD(I)*EPSMA2)
76C two-point derivatives always assumed necessary
77C maximum number of cycles over step size depends on strategy
78 XTF = X(I)
79 STEPB4 = 0.
80C loop as little as possible here!
81 DO 45 ICYC= 1, NCYC
82C ........ theoretically best step
83 OPTSTP = SQRT(DFMIN/(ABS(G2(I))+EPSPRI))
84C step cannot decrease by more than a factor of ten
85 STEP = MAX(OPTSTP, ABS(0.1*GSTEP(I)))
86C but if parameter has limits, max step size = 0.5
87 IF (GSTEP(I).LT.ZERO .AND. STEP.GT.0.5) STEP=0.5
88C and not more than ten times the previous step
89 STPMAX = 10.*ABS(GSTEP(I))
90 IF (STEP .GT. STPMAX) STEP = STPMAX
91C minimum step size allowed by machine precision
92 STPMIN = MAX(VRYSML, 8.*ABS(EPSMA2*X(I)))
93 IF (STEP .LT. STPMIN) STEP = STPMIN
94C end of iterations if step change less than factor 2
95 IF (ABS((STEP-STEPB4)/STEP) .LT. TLRSTP) GO TO 50
96C take step positive
97 GSTEP(I) = SIGN(STEP, GSTEP(I))
98 STEPB4 = STEP
99 X(I) = XTF + STEP
100 CALL MNINEX(X)
101 CALL FCN(NPARX,GIN,FS1,U,4,FUTIL)
102 NFCN=NFCN+1
103C take step negative
104 X(I) = XTF - STEP
105 CALL MNINEX(X)
106 CALL FCN(NPARX,GIN,FS2,U,4,FUTIL)
107 NFCN=NFCN+1
108 GRBFOR = GRD(I)
109 GRD(I) = (FS1-FS2)/(2.0*STEP)
110 G2(I) = (FS1+FS2-2.0*AMIN)/(STEP**2)
111 X(I) = XTF
112 IF (LDEBUG) THEN
113 D1D2 = (FS1+FS2-2.0*AMIN)/STEP
114 WRITE (ISYSWR,41) I,GRD(I),STEP,STPMIN,OPTSTP,D1D2,G2(I)
115 41 FORMAT (I4,2G11.3,5G10.2)
116 ENDIF
117C see if another iteration is necessary
118 IF (ABS(GRBFOR-GRD(I))/(ABS(GRD(I))+DFMIN/STEP) .LT. TLRGRD)
119 + GO TO 50
120 45 CONTINUE
121C end of ICYC loop. too many iterations
122 IF (NCYC .EQ. 1) GO TO 50
123 WRITE (CBF1,'(2E11.3)') GRD(I),GRBFOR
124 CALL MNWARN('D','MNDERI',
125 + 'First derivative not converged. '//CBF1)
126 50 CONTINUE
127C
128 60 CONTINUE
129 CALL MNINEX(X)
130 RETURN
131C . derivatives calc by fcn
132 100 DO 150 IINT= 1, NPAR
133 IEXT = NEXOFI(IINT)
134 IF (NVARL(IEXT) .GT. 1) GO TO 120
135 GRD(IINT) = GIN(IEXT)
136 GO TO 150
137 120 DD = (BLIM(IEXT)-ALIM(IEXT))*0.5 *COS(X(IINT))
138 GRD(IINT) = GIN(IEXT)*DD
139 150 CONTINUE
140 200 RETURN
141 END
Note: See TracBrowser for help on using the repository browser.