function [r,fvalue] = newton(f,fprime,x1,tolf,tolx,told,options,maxiter)
%
%    Newton.m:  A Function which uses Newton's Method
%               to find a root of the function f(x).
%
%    Example: newton('squared','twox',2+3i)
%
%    Inputs:  f -- the name of the function to evaluate
%             fprime -- the name of a function which returns the
%                       derivative for f(x)
%             x1 --  the initial guess for a root
%             tolf -- Stop when the function get closer to 
%                       zero than this value: Default 1e-10
%             tolx -- Stop when the iterates in x change by
%                       this size or smaller: Default 1e-10
%             told -- Stop with Error if derivative is too small
%                       Default 1e-8    
%             options -- If 0 or empty, no printouts
%                        If 1, print out each iterate and the function value.
%             maxiter -- Maximum number of iterations
%                       Default 100    
%
%    Outputs:  r -- the best guess at the root.
%              f -- the value of the function at the root.
%
if nargin<3 || isempty(f) || isempty(fprime) || isempty(x1) % check for enough arguments
   disp('The function Newton requires at least three arguments:')
   disp('Use "help newton" to get more information.')
   return
end

if nargin<8 || isempty(maxiter)       % set up defaults for maximum iterations 
   maxiter=100;
end
if nargin<7 || isempty(options)       % set up defaults for options 
   options=1;
end
if nargin<6 || isempty(told),    % set up defaults for derivative tolerances
   told=1e-8;
end
if nargin<5 || isempty(tolx)    % set up defaults for X tolerance
   tolx=1e-10;
end
if nargin<4 || isempty(tolf)    % set up defaults for F tolerance
   tolf=1e-10;
end
%   Done with argument checking
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

funct = f(x1);                % evaluate the function f(x1)
count = 0;        % set up iteration counter

x0=x1-tolx-1;   % Set pretend previous guess so that we pass tolx test 1st time.

if options==1,    % display before first iterate if options==1
  fprintf('%2i: x=%18.12e, f=%18.12e\n',count,norm(x1),norm(funct));       
end    %end of if options

% Now iterate until tolerances are met
while norm(funct) > tolf && norm(x1-x0)> tolx && count<maxiter,
   count=count+1;
   x0=x1;                     % set old x equal to new
   derv = fprime(x0);   % evaluate the function fprime(x0)	

   if(norm(derv) < told)       % Check that derivative is not too small
      disp('Error: Derivative less than critical tolerance level')
      disp('       Use "help newton" for details')
      return
   end
   x1 = x0 - derv\funct;      % get the new x
   funct = f(x1);       % evaluate the function
   if options==1,             % display iterates if options==1
 	  fprintf('%2i: x=%18.12e, f=%18.12e\n',count,norm(x1),norm(funct));       
   end    %end of if options
end   %end of while

if count >=maxiter
    fprintf('Error: Maximum number %i of iterations exceeded.\n',maxiter);
end

r=x1;                % set return values
fvalue=funct;
