matlab - 如何找到方程拟合参数的统计量
问题描述
例如:a
、b
和c
n 是三个常数,需要在特定方程中使用数据拟合方法计算。
如何计算自定义方程(例如二次高原方程)的参数的统计数据(平均值、标准差、方差、偏度值和学生 t 检验值)?
例子:
x=[0,40,80,100,120,150,170,200],
y=[1865,2855,3608,4057,4343,4389,4415,4478]
y=a*(x+n)^2+b*(x+n)+c, x < xc(Ymax) ....(1) y=yp, x >= xc(Ymax) ....(2)
我已经通过给定的代码拟合了这个方程:
yf = @(b,x) b(1).*(x+n).^2+b(2)*(x+n)+b(3); B0 = [0.006; 21; 1878];
[Bm,normresm] = fminsearch(@(b) norm(y - yf(b,x)), B0); a=Bm(1);
b=Bm(2); c=Bm(3); xc=(-b/(2*a))-n; p=p=a*(xc+n)^2+b*(xc+n)+c;
if (x < xc)
yfit = a.*(x+n).^2+ b*(x+n)+c;
else
yfit = p;
end
plot(x,yfit,'*')
hold on; plot(x,y); hold off
注意:我已经使用了该polyfit
命令,它很有帮助并为我提供了结果。但是,我真的觉得它不合适,因为没有自定义方程的选项。我可以通过任何代码找到这些统计信息吗?
解决方案
问题 1、2 和 4) 如果您对方程系统有先前的了解,好的做法是设置接近最终结果的初始值:
你所拥有的是一个超定的线性方程组。
y(1) = a*x(1)^2 + b*x(1) + c
y(2) = a*x(2)^2 + b*x(2) + c
y(3) = a*x(3)^2 + b*x(3) + c
…
y(n) = a*x(n)^2 + b*x(n) + c
or in general:
y = A*X, where
A = [a; b; c]
X = [x(1)^2 x(1) 1;
x(2)^2 x(2) 1;
x(3)^2 x(2) 1;
...
x(n)^2 x(n) 1]
拟合超定系统(因为它没有解)的一种常见做法是“最小二乘拟合”(mldivide,\(链接))
x=[0; 40; 80; 100; 120; 150; 170; 200];
y=[1865; 2855; 3608; 4057; 4343; 4389; 4415; 4478];
X = [x.^2 x ones(numel(x),1)];
A = y\X;
a0=A(1); %- initial value for a
b0=A(2); %- initial value for b
c0=A(3); %- initial value for c
当您自定义 X 和 A 时,您可以自定义方程式
但您也可以将初始值设置为 1,它对结果的影响应该可以忽略不计。更多与问题 4相关
a0=1;
b0=1;
c0=1;
或随机值
rng(10);
A = rand(3,1);
a0=A(1);
b0=A(2);
c0=A(3);
问题 3 - 统计 如果您需要对优化过程的监控进行更多控制,请使用更通用的匿名函数形式(在下面的代码中> myfun)来保存参数的所有中间值(a_iter、b_iter、c_iter)
function Fiting_ex()
global a_iter b_iter c_iter
a_iter = 0;
b_iter = 0;
c_iter = 0;
x=[0; 40; 80; 100; 120; 150; 170; 200];
y=[1865; 2855; 3608; 4057; 4343; 4389; 4415; 4478];
X = [x.^2 x ones(numel(x),1)];
A = y\X;
a0=A(1);
b0=A(2);
c0=A(3);
B0 = [a0; b0; c0];
[Bm,normresm] = fminsearch(@(b) myfun(b,x,y),B0);
a=Bm(1);
b=Bm(2);
c=Bm(3);
xc=-b/(2*a);
p=c-(b^2/(4*a));
yfit = zeros(numel(x),1);
for i=1:numel(x)
if (x(i) < xc)
yfit(i) = a.*x(i).^2+ b*x(i)+c;
else
yfit(i) = p;
end
end
plot(x,yfit,'*')
hold on;
plot(x,y);
hold off
% Statistic on optimization process
a_mean = mean(a_iter(2:end)); % mean value
a_var = var(a_iter(2:end)); % variance
a_std = std(a_iter(2:end)); % standard deviation
function f = myfun(Bm, x, y)
global a_iter b_iter c_iter
a_iter = [a_iter Bm(1)];
b_iter = [b_iter Bm(2)];
c_iter = [c_iter Bm(3)];
yf = Bm(1)*(x).^2+Bm(2)*(x)+Bm(3);
a=Bm(1);
b=Bm(2);
c=Bm(3);
xc=-b/(2*a);
p=c-(b^2/(4*a));
yfit = zeros(numel(x),1);
for i=1:numel(x)
if (x(i) < xc)
yfit(i) = a.*x(i).^2+ b*x(i)+c;
else
yfit(i) = p;
end
end
f = norm(y - yfit);
推荐阅读
- ios - 功能未在位置触发的通知应用程序中触发
- docker - 运行串联命令失败
- html - 角 10 | 不同的 ID 类型 | 如何使用 css 文件添加 css 样式
- docker - 如何运行 gcr.io/google-containers/echoserver:1.8 图像?
- python - Flask Swagger UI 无法找到 swagger.json
- javascript - 从 SASS 文件中导入 npm 包(带有字体)
- amazon-web-services - 如何定期自动刷新 RDS 表中的数据?
- python-3.x - 如何重载python集以接受重复项?
- azure - Azure PaaS 到 PaaS 网络通信
- json - 使用 jq 解析 json 值