% Function mfile descent.m % Implements the method of steepest descent in 2D. % User must supply an inline function f(x,y) % ( if f is written in an Mfile, the code will not work) % and a vector corners = [a b c d] of the rectangle in which % the minimum is thought to lie. N is the number of iterations. % The call is descent(f,corners, N) function out = descent(f,corners,N) % make symbolic expression for f(x,y) to compute the derivatives syms x y; ff = sym(f(x,y)); ffx = diff(ff,x); ffy = diff(ff,y); % make numerical inline functions for fx and fy fx = inline(vectorize(ffx),'x', 'y') fy = inline(vectorize(ffy),'x', 'y') % plot contours of f(x,y) a = corners(1); b = corners(2); c = corners(3); d = corners(4); xmesh = linspace(a,b,101); ymesh = linspace(c,d,101); [X,Y] = meshgrid (xmesh, ymesh); Z = feval(f,X,Y); f1 = min(min(Z)); f2 = max(max(Z)); levels = linspace(log(f1+.01),log(f2), 21); levels = exp(levels); contour(X,Y,Z,levels) hold on axis equal hold on % get starting point by clicking on the contour plot p = ginput(1); plot(p(1), p(2), '*r') x = zeros(N,1); y = x; x(1) = p(1); y(1) = p(2); for n = 2:N % v is the direction of steepest descent v = -[feval(fx, x(n-1),y(n-1)), feval(fy,x(n-1), y(n-1))]; l = norm(v); if l < eps sprintf(' grad f = 0, n = %2d x = %2.5f y = %2.5f', n-1, x(n-1), y(n-1)) break end v = v/l; tmax = .1*max(b-a, d-c); % construct the line of x y values along which we search for the min of f M = 10001; t = linspace(0, tmax, M); xvals = t*v(1); yvals = t*v(2); xx = x(n-1) + xvals; yy = y(n-1) + yvals; fvals = feval(f,xx,yy); % plot(xx,fvals) [m,j]= min(fvals); for k = 1:10 % if the min occurs at the endpoint, we extend the search line and % look further. This can be done at most 10 times. if j == M xx = xx(M) + xvals; yy = yy(M) + yvals; fvals = feval(f,xx,yy); % plot(xx,fvals) [m,j] = min(fvals); else break end end x(n) = xx(j); y(n) = yy(j); disp('hit return to continue ') pause plot(x(n), y(n), '*r') end plot(x,y, 'r') disp( ' x y f(x,y) ') [x,y,feval(f,x,y)] hold off