Page 166 - Compact Numerical Methods For Computers
P. 166
One-dimensional problems 155
Algorithm 17. Minimisation of a function of one variable (cont.)
if s1<s0 then
begin {Here we can proceed to try to find s2 now in same direction.}
repeat {success-failure search loop}
st := st*a1; {increase the stepsize after a success}
x2 := x1+st; {get next point in the series}
s2 := fn1d(x2,notcomp); if notcomp then s2 := big; ifn := ifn+1;
if s2<s1 then
begin {another success}
s0 := s1; s1 := s2; {In order to continue search,}
x0 := x1; x1 := x2; {we copy over the points.}
write(‘Success1‘);
end
else {‘failure’ after ‘success’ ==> V-shaped triple of points}
begin
tripleok := true; (to record existence of the triple}
write(‘Failure1‘);
end;
until tripleok, (End of the success-failure search for}
end {s1<s0 on first pair of evaluations}
else
begin {s1>=s0 on first pair of evaluations in this major cycle, so we
must look for a third point in the reverse search direction.}
st := a2*st; {to reverse direction of search and reduce the step size}
tt2 := s0; s0 := s1; s1 := tt2; {to swap function values}
tt2 := x0; x0 := x1; x1 := tt2; {to swap arguments}
repeat
x2 := x1+st; {get the potential third point}
s2 := fn1d(x2,notcomp); if notcomp then s2 := big; ifn := ifn+1;
if s2<s1 then
begin {success in reducing function -- keep going}
s0 := s1; s1 := s2, x0 := x1; x1 := x2; {reorder points}
st := st*a1; {increase the stepsize maintaining direction}
write(‘Success2‘);
end
else
begin {two failures in a row ensures a triple in a V}
tripleok := true; write(‘Failure2’);
end;
until tripleok; {End of success-failure search}
end, {if s1<s0 for first pair of test points}
{Now have a V of points (x0,s0), (x1,s1), (x2,s2).}
writeln; writeln(‘Triple (‘,x0,‘,‘,s0,*)‘);
writeln(‘(‘,x1,‘,‘,s1,‘)‘); writeln(’(‘,x2,‘,‘,s2,‘)‘);
tt0 := x0-x1; {to get deviation from best point found. Note that st
holds value of x2-x1.}
tt1 := (s0-s1)*st; tt2 := (s2-s1)*tt0; {temporary accumulators}
if tt1<>tt2 then {avoid zero divide in parabolic inverse interpolation}
begin
st := 0.5*(tt2*tt0-tt1*st)/(tt2-ttl1; {calculate the step}
Xii := x1+st;
writeln(‘Paramin step and argument :‘,st,’ ‘,xii);
if (reltest+xii)<>(reltest+x1) then