ODE lsqcurvefit改变了ode方程

时间:2013-12-11 20:24:47

标签: matlab curve-fitting ode

我正在尝试使用ODE系统对某些数据拟合曲线。 ODE系统根据预定义的时间点改变到不同的ODE系统。

我在下面构建了一个简单的例子来说明。

function examplefitting

init = [1];
expdata = [10;40;70;76;80;90;101;110;150;180;200;202;215;240;245]';
time = [5;10;15;20;25;30;35;40;50;55;60;65;70;75;80]';

[x,resnorm] = lsqcurvefit(@data,init,time,expdata);

function z = data(init,time)

alpha = init(1);
y0 = 100;
   tout = [];
   yout = [];
   for i = 2:5
       tvec = [0 15 30 50 65];
       u = [1 0 1 0 1];

       [t y] = ode23s(@Model,[tvec(i-1) tvec(i)],y0,[],alpha,u(i-1));
       nt = length(t);
       tout = [tout;t];
       yout = [yout;y];

       y0 = [y(nt,1)];

   end

z = yout;

function Y = Model(t,y,alpha,u)
if u == 0

Y(1) = y(1).^alpha;

elseif u == 1

Y(1) = alpha*y(1);

end

Y = Y.';

你可以看到,因为我必须停止积分器并重置它,输出的长度和原始数据输入的长度不同。这会导致“功能值和YDATA大小不相称”的错误。有没有一种方法可以提取最合适的alpha,因为它出现在两个不同的ODES系统中,根据时间切换。

1 个答案:

答案 0 :(得分:0)

可能还没回答,但有些建议。

首先,将参数传递给集成函数的现代(和更快)方法是使用匿名函数:

[t,y] = ode23s(@(t,y)Model(t,y,alpha,u(i-1)),[tvec(i-1) tvec(i)],y0);

其次,你要两次追加一些值。将tvecu移到for循环之外,因为它们是常量,并将toutyout初始化为初始时间和状态

tout = tvec(1);
yout = y0;

然后,在你的循环中添加如下新数据:

tout = [tout;t(2:end)];
yout = [yout;y(2:end,:)];

最后,我想知道您是否可以通过指定固定的步长输出来解决您的问题。您可以通过将tspan设置为两个以上元素的向量来完成此操作。然后积分器只会在那些特定时间返回点。