# How to combine 2 Fits done with cftool

17 views (last 30 days)
Niklas Kurz on 24 Jun 2020
Commented: Niklas Kurz on 26 Jun 2020
I know right there's kind of an article in matlab concering this topic, but I don't grasp it. So here again, I set up 2 fits and "generated code" so there are 2 .m files with the fit including. How do I combine them? I tried to create 2 fits in the toolbox and generated code afterwards, but it still plots 2 seperate plots. Would be great if you could help me out.

dpb on 24 Jun 2020
Well, that will kinda' depend upon what you're trying to do and possibly how different the two fits are in what they use for input data and all...I rarely ever use the tool so am not terribly familiar with its code generation--what I recollect is being machine-written it's pretty verbose in comparison to what one could do just using the fit() function ...
What might make sense would be to just attach the files as we can tell nothing about your case from here...
Niklas Kurz on 25 Jun 2020
alright, the fits are actually almost the same, just applied to different x- and y-values:
The first one goes like:
%% Fit: 'untitled fit 1'.
[xData, tmp] = prepareCurveData( Fqr, Prem );
yData = tmp+pi/2;
% Set up fittype and options.
ft = fittype( 'a*atan(2*b*t/3.83^2-t^2)+pi/2', 'independent', 't', 'dependent', 'y' );
opts = fitoptions( 'Method', 'NonlinearLeastSquares' );
opts.Display = 'Off';
opts.StartPoint = [0.0496544303257421 0.902716109915281];
% Fit model to data.
[fitresult, gof] = fit( xData, yData, ft, opts );
% Plot fit with data.
figure( 'Name', 'untitled fit 1' );
h = plot( fitresult, xData, yData,'x');
set(h,'LineWidth',2,'Markersize',7.5)
legend( h, 'Prem vs. Fqr', 'untitled fit 1', 'Location', 'NorthEast', 'Interpreter', 'none' );
% Label axes
xlabel( 'Fqr', 'Interpreter', 'none' );
ylabel( 'Prem', 'Interpreter', 'none' );
grid on
legend({'Phasenverschiebung','Fit: $(-1,02 \pm 0,07) \cdot \tan^{-1}(\frac{2\cdot (27,59 \pm 0,27)\cdot \omega}{3,83^2-\omega^2})$'},'Interpreter','latex','FontSize',14)
xlabel({'$\omega$ in rad'},'Interpreter','latex','FontSize',14)
ylabel({'Phasenverschiebung $\Delta \varphi$ in rad'},'Interpreter','latex','FontSize',14)
and the second one:
%% Fit: 'untitled fit 1'.
[xData, tmp] = prepareCurveData( Fq2r, Prem2 );
yData = tmp+pi/2;
% Set up fittype and options.
ft = fittype( 'a*atan(2*b*t/3.82^2-t^2)+pi/2', 'independent', 't', 'dependent', 'y' );
opts = fitoptions( 'Method', 'NonlinearLeastSquares' );
opts.Display = 'Off';
opts.StartPoint = [0.425259320214135 0.312718886820616];
% Fit model to data.
[fitresult, gof] = fit( xData, yData, ft, opts );
% Plot fit with data.
figure( 'Name', 'untitled fit 1' );
h = plot( fitresult, xData, yData );
set(h,'LineWidth',2,'Markersize',7.5)
legend( h, 'Prem2 vs. Fq2r', 'untitled fit 1', 'Location', 'NorthEast', 'Interpreter', 'none' );
% Label axes
xlabel( 'Fq2r', 'Interpreter', 'none' );
ylabel( 'Prem2', 'Interpreter', 'none' );
grid on
legend({'Phasenverschiebung bei $I = 0,25 A$','Fit: $(-1,26 \pm 0,20) \cdot \tan^{-1}(\frac{2\cdot (26,59 \pm 0,65)\cdot \omega}{3,83^2-\omega^2})$'},'Interpreter','latex','FontSize',14)
xlabel({'$\omega$ in rad'},'Interpreter','latex','FontSize',14)
ylabel({'Phasenverschiebung $\Delta \varphi$ in rad'},'Interpreter','latex','FontSize',14)
dpb on 25 Jun 2020
Basically, just string the two together -- you'll have to create a second set of graphics handle variables for the two to keep from overwriting the previous for h and the legend strings merged to a single call at the end.
Also call hold on to add the second to the first axis and remove the duplicated label call...

dpb on 25 Jun 2020
Edited: dpb on 25 Jun 2020
%% Fit: 'untitled fit 1'.
[xData1, tmp] = prepareCurveData( Fqr, Prem );
yData1 = tmp+pi/2;
% Set up fittype and options.
% Type is same for both so only need one object initially
ft = fittype( 'a*atan(2*b*t/3.83^2-t^2)+pi/2', 'independent', 't', 'dependent', 'y' );
opts = fitoptions( 'Method', 'NonlinearLeastSquares' );
opts.Display = 'Off';
% Will change the start point between two -- may or may not matter...
opts.StartPoint = [0.0496544303257421 0.902716109915281];
% Fit model to data.
% Make a first variable set unique
[fitresult1, gof1] = fit( xData, yData, ft, opts );
% Plot fit with data.
%figure( 'Name', 'untitled fit 1' ); % let default handle it...
h(1) = plot( fitresult1, xData1, yData1,'x');
% NOW DATA FOR SECOND
[xData2, tmp] = prepareCurveData( Fq2r, Prem2 );
yData2 = tmp+pi/2;
% and the other start points, fit...
opts.StartPoint = [0.425259320214135 0.312718886820616];
[fitresult2, gof2] = fit( xData2, yData2, ft, opts );
hold on % add to existing plot
h(2) = plot( fitresult2, xData2, yData2 );
% set both line handles in h array...
set(h,'LineWidth',2,'Markersize',7.5)
grid on
legend({'Phasenverschiebung','Fit: $(-1,02 \pm 0,07) \cdot \tan^{-1}(\frac{2\cdot (27,59 \pm 0,27)\cdot \omega}{3,83^2-\omega^2})$'}, ...
{'Phasenverschiebung bei $I = 0,25 A$','Fit: $(-1,26 \pm 0,20) \cdot \tan^{-1}(\frac{2\cdot (26,59 \pm 0,65)\cdot \omega}{3,83^2-\omega^2})$'}, ...
'Interpreter','latex','FontSize',14)
xlabel({'$\omega$ in rad'},'Interpreter','latex','FontSize',14)
ylabel({'Phasenverschiebung $\Delta \varphi$ in rad'},'Interpreter','latex','FontSize',14)
is a first cut

Niklas Kurz on 25 Jun 2020
First of Thank you so much for your effort: However, I guess I should have mentionned that the 2 fits doesn't have same Size, as:
Fqr = [400 500 525 550 575 600 625 650 675 700 750].*(2*pi/1000)
Prem = [0.277 0.527 0.637 0.628 1.034 1.561 2.167 2.727 2.758 2.749 2.861]-pi/2
Fq2r = [300 400 500 525 550 575 600 625 650 675 700 750].*(2*pi/1000)
Prem2 = [0.094 0.220 0.253 0.255 0.517 1.111 2.630 3.005 3.090 2.990 3.063 2.936]-pi/2
After running the code Fqr and Fq2r also have been tangeled up. So, how to fix it?
dpb on 25 Jun 2020
Different size won't matter...all I see is missed adding the '1' to end of X|YData in first call to fit()...
h(1) = plot( fitresult1, xData1, yData1,'x');
should fix that.
You'll just have to step through and debug...all it's doing is calling fit twice with the two data sets after the preparatory work is done.
The other way to approach it is to take one of the original copies, turn it from a script into a function using generic data arguments and then call that function with the two data sets in turn. Then you could rearrange to return the fit results and plot them together instead of asking the fitting routine to also do the plotting...or not, your choice.
Niklas Kurz on 26 Jun 2020
yea, u're totally right, plotting data and adding fit curve with parameters of cftool is just more effective then this tangled string. Sometimes my view is just restricted. Thank you so much for leading me through!