Fitting uneven data to a function
7 次查看(过去 30 天)
显示 更早的评论
Hi!
So, I recently asked a question as to how to solve a summation (link) and I think I have the function working but I am having issues fitting it to my unevenly spaced data. I have attached the data file (column 4 is x data and 3 is y data). I am scaling the data as you can see in the figure (by taking an inverse square root of the x data) attached at the bottom. Is this a data problem? Or can I make a good fit by adding something like weights? Or do I need to use a different function altogether?
Function itself is as such:
![](https://www.mathworks.com/matlabcentral/answers/uploaded_files/1113900/image.png)
MATLAB function I wrote to give as an input to the fitting function.
function I_num = CurveFitD(x, t)
%CurveFitD We want to fit the I(t)=f(t) to a custom function.
% For a bounded layer we have an expression which can yield us the
% thickness of the polymer layer (in centimeters). We have to fit the transient to this
% equation to calculate the layer thickness.
% Constants
I_num = zeros(size(t));
% Bounded Cottrell
for i = 1:length(t)
for k = 1:42
I_num(i) = I_num(i) + (-1).^k.*exp(-((k*x(1))^2)./(x(2).*t(i)));
end
I_num(i) = sqrt(x(2)./(pi.*t(i))).*(x(3)./x(1)).*(1+2.*I_num(i));
end
end
I am calling this function using lsqcurvefit as given. As you can see I have an idea of the parameters I want to extract.
%% Nonlinear Curve-Fitting (Data-Fitting 'lsq')
%%
t = E3PS_Whole.CorrectedTimes;
I_exp = E3PS_Whole.WE1CurrentA;
invsqrt = 1./sqrt(t);
options = optimoptions('lsqcurvefit','Algorithm','trust-region-reflective',...
'OptimalityTolerance',1e-12,...
'StepTolerance', 1e-12,...
'FunctionTolerance',1e-12,...
'FiniteDifferenceType',"central");
% x(1)=d; x(2)=D_e; x(3)=deltaQ
lb = [1e-07; 1e-10; 1e-09];
ub = [1e-03; 1e-06; 1e-05];
x_0 = [4e-05; 1e-07; 1e-06];
[x,resnorm,residual,exitflag,output]=lsqcurvefit(@CurveFitD, x_0, t, I_exp, lb, ub, options);
I_num = CurveFitD(x, t);
% I vs E for Experimental and Calculated
figure(4);
plot(invsqrt, I_exp, 'ro', 'LineWidth', 1);
hold on;
plot(invsqrt, I_num, 'b--', 'LineWidth',2);
xlabel('1/{\surd{t}} / s^{-1/2}'); ylabel('I / A');
legend('Experimental', 'Numerical');
Output looks like this.
![](https://www.mathworks.com/matlabcentral/answers/uploaded_files/1113890/image.jpeg)
4 个评论
Matt J
2022-9-1
I don't yet have the grasp of how to run code here but will try to learn about it.
Use the Run button,
![](https://www.mathworks.com/matlabcentral/answers/uploaded_files/1113985/image.png)
Torsten
2022-9-2
Define x(1) = sqrt(D)/d and x(2) = deltaq as your model parameters and write your model in these two parameters.
Using three parameters as you do makes your model overfitted.
回答(1 个)
Matt J
2022-9-1
编辑:Matt J
2022-9-1
Or do I need to use a different function altogether?
The first thing I notice is that your model is over-parametrized. You are writing it in terms of 3 parameters when in fact there are only 2 degrees of freedom, since the model depends on d and D only through the ratio d^2/D.
Also, one of the parameters
is merely a linear scaling constant, and can be eliminated from the iterative fitting process as well if you do the curve fit using fminspleas,
![](https://www.mathworks.com/matlabcentral/answers/uploaded_files/1113955/image.png)
Solving for 1 unknown should be pretty robust, without the need for data weighting, but fminspleas does let you provide weights if desired.
4 个评论
另请参阅
类别
在 Help Center 和 File Exchange 中查找有关 Least Squares 的更多信息
产品
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!