在matlab中使用cftool拟合非线性函数曲线

时间:2014-02-04 12:01:15

标签: matlab math

我需要使用非线性函数来拟合数据:

y=a+b*cos(c*x+d)+e*exp(f*x);

其中a,b,c,d,e和f是要找到的系数。我在cftool中使用了自定义方程方法,结果不好,那么如何在cftool中调整StartPoint以获得更好的结果?否则,还有其他方法可以解决我的问题吗?非常感谢。

这是我的数据,每个都在1 * 35:

    x = [1970:2004];
    y = [46808,49416,53094,57237,56677,56198,59673,61826,64158,65220,63108,60944,59543,58779,59882,60087,61825,63104,64963,66902,66443,67061,67273,67372,68679,69995,71522,73292,73932,75826,76954,78105,78439,79892,82631];

好的,Dan,这是关于cftool的代码,该函数由cftool的自定义方程式生成

% This file include two functions:
% 1. Main: testForFit.m
% 2. Function generated by cftool
function testForFit
clc; clear all;
x = 1970:2004;
y = [46808,49416,53094,57237,56677,56198,59673,61826,64158,65220,63108,60944,59543,58779,59882,60087,61825,63104,64963,66902,66443,67061,67273,67372,68679,69995,71522,73292,73932,75826,76954,78105,78439,79892,82631];
plot(x, y, 'or')
[fitresult, gof] = createFit(x, y)
end

function [fitresult, gof] = createFit(x, y)
%CREATEFIT(X,Y)
%  Create a fit.
%
%  Data for 'untitled fit 1' fit:
%      X Input : x
%      Y Output: y
%  Output:
%      fitresult : a fit object representing the fit.
%      gof : structure with goodness-of fit info.
%
%  See also FIT, CFIT, SFIT.
%  Auto-generated by MATLAB on 04-Feb-2014 00:23:03
%% Fit: curve fitting of gived form of function.
[xData, yData] = prepareCurveData( x, y );

% Set up fittype and options.
ft = fittype( 'a+b*cos(c*x+d)+e*exp(f*x)', 'independent', 'x', 'dependent', 'y' );
% ft = fittype( 'a+e*exp(f*x)', 'independent', 'x', 'dependent', 'y' );
opts = fitoptions( 'Method', 'NonlinearLeastSquares' );
opts.Display = 'Off';

% http://stackoverflow.com/questions/21551951/fitting-curve-with-nonlinear-function-using-cftool-in-matlab
% Firstly, give the estimation, then calculate it
% funlist={1, @(p,x) cos(p(1)*x+p(2)), @(p,x) exp(p(3)*x)};
% NLPstart = [0.605 -3159.659 0.02369];
% [cdf,abe] = fminspleas(funlist,NLPstart,x,y)
% c=cdf(1); d=cdf(2); f=cdf(3);
% a=abe(1); b=abe(2); e=abe(3);
% opts.StartPoint = [a b c d e f];

% How to give the value of StartPoint ?
opts.StartPoint = [0.957166948242946 0.485375648722841 0.8002804688888 0.141886338627215 0.421761282626275 0.915735525189067];
% opts.StartPoint = [31950 1557 0.605 -3159.659 1.183e-16 0.02369];

% Fit model to data.
[fitresult, gof] = fit( xData, yData, ft, opts );

% Plot fit with data.
figure( 'Name', 'curve fitting' );
h = plot( fitresult, xData, yData );
legend( h, 'y vs. x', 'curve fitting', 'Location', 'NorthEast' );
% Label axes
% 31950 1557 0.605 -3159.659 1.183e-16 0.02369
% title('31950+1557*cos(0.605*x-3159.659)+1.183e-16*exp(0.02369*x)')
xlabel( 'x' );
ylabel( 'y' );
grid on
% x = [1970:2004];
% y = [46808,49416,53094,57237,56677,56198,59673,61826,64158,65220,63108,60944,59543,58779,59882,60087,61825,63104,64963,66902,66443,67061,67273,67372,68679,69995,71522,73292,73932,75826,76954,78105,78439,79892,82631];
% Baidu Zhidao
% http://zhidao.baidu.com/question/198731054514100005.html?push=keyword
end

如果StartPoint不正确,将会出现一些错误......

1 个答案:

答案 0 :(得分:0)

我没有CurveFit工具箱,但据说在您选择曲线类型的位置附近有一个“适合选项”按钮,从而产生一个对话框,您可以在其中选择自己的初始点。

我还建议您尝试FMINSPLEAS,这可以利用y与6个参数中的3个线性相关的事实。您还需要提供非线性参数NLPstart=[c,d,f]

的初始猜测
funlist={1, @(p,x) cos(p(1)*x+p(2)), @(p,x) exp(p(3)*x)};

[cdf,abe] = fminspleas(funlist,NLPstart,x,y);

c=cdf(1); d=cdf(2); f=cdf(3);
a=abe(1); b=abe(2); e=abe(3);