MATLAB: Getting better accuracy with Lsqcurvefit

lsqcurvefit

Hi, I am trying to use lsqcurvefit to do curvefitting of results from an impedance measurement. At the moment I have created data from the same function that I use for lsqcurvefit to generate its own data, thus eliminating any possibility that the model and the data do not match. I have managed to provide the data to the function in a manner where the imaginary part of the values have been added to the end of the real part of the values in a single data set. The whole function works now but I cannot manage to get decent curve fits. The plots show that the new parameters that lsqcurvefit finds are closer to achieving the desired curvefit but not good enough. I tried varying the TolX and TolY values but to no avail. I dont think I understand very well how to manipulate the options of lsqcurvefit and would like some help on that.
%----main script----
f=logspace(1.30103,6,50);
xtest=[100e3 1e-9];
testdata=model(xtest,f);
x1=[210e3 2.2e-9];
lb=[10e2,1e-10];
ub=[300e3,1e-8];
optoptions=optimset('TolX',0.001,'TolFun',0.001);
[x2,resnorm]=lsqcurvefit(@model,x1,f,testdata,lb,ub,options);
resnorm
x2
plotdata(f,x1,x2,testdata);
%---end main script
%-----Impedance Model----
function [RX]=model(xo,f)
sres=xo(1);
pcap=xo(2);
Z=1./((1/sres)+(2*pi*1i*pcap.*f));
R=real(Z);
X=imag(Z);
RX=setdata(R,X);
end
%%%-----End Impedance Model---
%-----Set Data----
function [dataout]=setdata(datain1,datain2)
dataout=[datain1 datain2]';
end
%%%-----End Set Data----
%-----Plot function---
function plotdata(freq,x1,x2,measdata)
RX=model(x1,freq);
RX2=model(x2,freq);
R=RX(1:size(RX)/2);X=RX(1+size(RX)/2:end);
R2=RX2(1:size(RX2)/2);X2=RX2(1+size(RX2)/2:end);
R3=measdata(1:size(RX2)/2);X3=measdata(1+size(RX2)/2:end);
subplot(2,1,1)
semilogx(freq,R,freq,R2,'--p',freq,R3,'.r');legend('Initial','New','Data');grid;
subplot(2,1,2)
semilogx(freq,X,freq,X2,'--p',freq,X3,'.r');legend('Initial','New','Data');grid;
end
%----end plot function----
Affar

Best Answer

The problem may be that your two parameters have such very different magnitudes, so the fit can probably not discriminate the second parameter very well. Try rescaling so the parameters have similar magnitudes.
You might find it interesting to look at a plot of the function to be minimized:
g = @(x) sum((model(x,f)-testdata).^2); % sum of squares of the residuals
a = linspace(lb(1),ub(1),100);
b = linspace(lb(2),ub(2),100);
[A,B] = meshgrid(a,b);
fitSurf = 0*Ai;
for ii=1:numel(A)
fitSurf(ii) = g([A(ii) B(ii)]);
end
contour(a,b,fitSurf,20)