curve fitting exponential function with two terms
    19 vues (au cours des 30 derniers jours)
  
       Afficher commentaires plus anciens
    
Update: I need help curve fitting this set of points with an exponential function with two terms nicely.
% Curve Fit
x = [6500 6350 6000 5400 4500];
y = [0 0.25 0.5 0.75 1.0];
theFit=fit(x' , y', 'exp2')
10 commentaires
  Image Analyst
      
      
 le 12 Nov 2023
				Sorry, but I don't believe you.  When I swap x and y, the fit looks great.
% Curve Fit
y = [6500 6350 6000 5400 4500];
x = [0 0.25 0.5 0.75 1.0];
theFit=fit(x' , y', 'exp2')
plot(theFit , x , y)
Réponses (3)
  Matt J
      
      
 le 11 Nov 2023
        
      Modifié(e) : Matt J
      
      
 le 11 Nov 2023
  
      You should normalize your x data
% Curve Fit
x = [6500 6350 6000 5400 4500]; 
      x=(x-mean(x))/std(x);
y = [0 0.25 0.5 0.75 1.0];
Also, I would recommend downloading fminspleas from the File Exchange 
and using it to generate an initial guess for fit():
e=@(a,xd)exp(a*xd);
flist={@(p,xd) e(p(1),xd)   , @(p,xd) e(p(2),xd)};
[bd,ac]=fminspleas(flist,[-1,1],x, y);
theFit=fit(x',y','exp2','StartPoint',[ac(1),bd(1),ac(2), bd(2) ])
plot(theFit,x,y)
5 commentaires
  Torsten
      
      
 le 12 Nov 2023
				
      Modifié(e) : Torsten
      
      
 le 12 Nov 2023
  
			x = [6500 6350 6000 5400 4500]; 
xt = (x-mean(x))/std(x);    
y = [0 0.25 0.5 0.75 1.0];
theFit=fit(xt',y','exp2')
theFit.b = theFit.b/std(x);
theFit.a = theFit.a*exp(-theFit.b*mean(x));
theFit.d = theFit.d/std(x);
theFit.c = theFit.c*exp(-theFit.d*mean(x));
theFit
plot(theFit,x,y)
  Matt J
      
      
 le 12 Nov 2023
				I mentioned in the comments that I needed to change my points (noticed an error in my work). 
All answers in this thread have been demonstrated using your new points.
  Matt J
      
      
 le 12 Nov 2023
        
      Modifié(e) : Matt J
      
      
 le 12 Nov 2023
  
      You can also use fit()'s normalizer,
x = [6500 6350 6000 5400 4500]; 
y = [0 0.25 0.5 0.75 1.0];
theFit=fit(x',y','exp2','Normalize','on')
plot(theFit,x,y)
2 commentaires
  Briana Canet
 le 12 Nov 2023
				
      Modifié(e) : Briana Canet
 le 12 Nov 2023
  
			
		
  Matt J
      
      
 le 12 Nov 2023
				
      Modifié(e) : Matt J
      
      
 le 12 Nov 2023
  
			If you need to explicitly manipulate the coefficients and fit function, you'll have to do the normalization manually:
% Curve Fit
x = [6500 6350 6000 5400 4500]; 
 xmu=mean(x);
 xstd=std(x);
y = [0 0.25 0.5 0.75 1.0];
theFit=fit((x-xmu)'/xstd,y','exp2');
% Monthly Cost
cost = x; 
costUtility = y;
% Plot Utility Points
figure;
plot(cost,costUtility,'*');
xlim([4500 6500]);ylim([0 1.25]);
yticks([costUtility 1.25]);
grid on;
xlabel('Monthly Cost ($)');
ylabel('Utility');
legend('Utility Points');
% Add utility curve fit
coeff=num2cell(coeffvalues(theFit));
[a,b,c,d]=deal(coeff{:});
curveX = linspace(4500,6500);
   X=(curveX-xmu)/xstd;
curveY = a*exp(b*X) + c*exp(d*X);
hold on;
plot(curveX,curveY,'Color','b');
legend('Utility Points','Utility Curve Fit');
  Alex Sha
      
 le 12 Nov 2023
        
      Modifié(e) : Alex Sha
      
 le 12 Nov 2023
  
      If taking the fitting function as: y=a*exp(b*x) + c*exp(d*x);
and also taking the data like below directly;
x = [6500 6350 5800 4900 4500];
y = [0 0.25 0.5 0.75 1.0];
The unique stable result should be:
Sum Squared Error (SSE): 0.00221359211819696
Root of Mean Square Error (RMSE): 0.0210408750682901
Correlation Coef. (R): 0.998229714370904
R-Square: 0.996462562653016
Parameter	Best Estimate        
---------	-------------        
a        	11.4185972844776     
b        	-0.000545792212445247
c        	-1.22298024843855E-22
d        	0.00759142468815435 

If add one more parameter, that is the fitting function become: y=a*exp(b*x)+c*exp(d*x)+e; the result will be perfect:
Sum Squared Error (SSE): 4.41584921368883E-29
Root of Mean Square Error (RMSE): 2.97181736103982E-15
Correlation Coef. (R): 1
R-Square: 1
Parameter	Best Estimate        
---------	-------------        
a        	-2.47788945923639E-15
b        	0.00505297753885221  
c        	332.002937639918     
d        	-0.00141137023194644 
e        	0.420769231934917  

11 commentaires
  Alex Sha
      
 le 13 Nov 2023
				It would be a good suggestion for Mathwork, although not claer how 1stOpt process such problem internally.
  Matt J
      
      
 le 13 Nov 2023
				MathWorks' fit() routine does have an internal normalization step which can be enabled,
However, if 1stOpt does something similar, it appears to be smart enough to post-transform the parameters and undo the effect of the data normalization.  fit() does not do that. 
Voir également
Catégories
				En savoir plus sur Fit Postprocessing dans Help Center et File Exchange
			
	Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!

















