怎么对点集进行傅里叶拟合,MATLAB的cftool只能进行到8级,八级往上又该怎么实现
不知道你这个问题是否已经解决, 如果还没有解决的话:来源:https://www.cnblogs.com/yabin/p/6417566.html
历史出错代码1
% 自变量和应变量
x = [
14.5200
15.2500
15.6000
16.4700
16.9200];
Y = [
116.2000
162.3000
176.1000
251.8000
290.2000];
% 被拟合的函数 用于 fit 函数
linearFun1 = 'a*x+b';
powerFun1 = 'a*x^b+c';
indexFun1 = 'a*exp(b*x)+c';
sinFun1 = 'a*sin(x+b)+c';
Fun1_array = {
linearFun1
powerFun1
indexFun1
sinFun1};
% 被拟合的函数的自变量 用于 fit 函数
linearX1 = {'x'};
powerX1 = {'x'};
indexX1 = {'x'};
sinX1 = {'x'};
X1_array = {
linearX1
powerX1
indexX1
sinX1};
% 被拟合的函数的系数 用于 fit 函数
linearCo1 = {'a','b'};
powerCo1 = {'a','b','c'};
indexCo1 = {'a','b','c'};
sinCo1 = {'a','b','c'};
Co1_array = {
linearCo1
powerCo1
indexCo1
sinCo1};
% 被拟合的函数 用于 nlinfit 函数
linearFun2 = @(x,Co2) Co2(1).*x+Co2(2);
powerFun2 = @(x,Co2) Co2(1).*x.^Co2(2)+Co2(3);
indexFun2 = @(x,Co2) Co2(1).*exp(Co2(2).*x)+Co2(3);
sinFun2 = @(x,Co2) Co2(1).*sin(x+Co2(2))+Co2(3);
Fun2_array = {
linearFun2
powerFun2
indexFun2
sinFun2};
% 设置系数的起始搜索点
startPos = [1,1];
% 待拟合函数的总数
length = size(Fun1_array,1);
% 拟合结果数组
% fitFunResult = zeros(size(Fun1_array));
% Co2Result = zeros(size(Fun1_array));
for i = 1:1:length
subplot(length,1,i);
string(Fun1_array(i))
string(X1_array(i))
Co1_array(i)
% 使用 fit 函数拟合
funType = fittype(string(Fun1_array(i)),'independent',string(X1_array(i)),'coefficients',Co1_array(i));
opt = fitoptions(funType);
set(opt,'StartPoint',startPos);
fitFunResult(i) = fit(x,Y,funType,opt);
% 打印结果
disp(fitFunResult(i));
% 画图
hold on;
plot(fitFunResult(i),'r',x,Y,'*');
% 使用 nlinfit 函数拟合
Co2Result(i) = nlinfit(x,Y,Fun2_array(i),startPos);
% 打印结果
disp('nlinfit拟合后的系数矩阵为:');
disp(Co2Result(i));
% 画图
hold on;
xmax = max(x);
xmin = min(x);
xnum = 2*length(x)+50;
x = linspace(xmin,xmax,xnum);
fun2 = Fun2_array(i);
y = fun2(x,Co2Result(i));
plot(x,y,'g');
legend('原始数据','fit拟合','nlinfit拟合');
end
错误警报:
错误使用 cellstr (第 44 行)
元素 1 不是字符串标量或字符数组。元胞输入的所有元素都必须为字符串标量或字符数组。
出错 fittype>iAssertValidVariableNames (第 1053 行)
names = cellstr( names );
出错 fittype>iSetVariableNames (第 1044 行)
iAssertValidVariableNames( variableName );
出错 fittype>iParseParameters (第 561 行)
obj = iSetVariableNames( obj, ‘coeff’, value );
出错 fittype>iCreateCustomFittype (第 429 行)
obj = iParseParameters(obj,varargin(2:end));
出错 fittype>iCreateFittype (第 353 行)
obj = iCreateCustomFittype( obj, varargin{:} );
出错 fittype (第 330 行)
obj = iCreateFittype( obj, varargin{:} );
主要是字符的传递有点费劲……
我试过 tostring 也不行,就不想搞了,不在一棵树上吊死了
之后试了一下,好像是因为元胞数组需要用 {} 提取数据hhh
% 自变量和应变量
x = [
14.5200
15.2500
15.6000
16.4700
16.9200];
Y = [
116.2000
162.3000
176.1000
251.8000
290.2000];
% 被拟合的函数 用于 nlinfit 函数
linearFun = @(x,Co2) Co2(1).*x+Co2(2);
powerFun = @(x,Co2) Co2(1).*x.^Co2(2)+Co2(3);
indexFun = @(x,Co2) Co2(1).*exp(Co2(2).*x)+Co2(3);
sinFun = @(x,Co2) Co2(1).*sin(x+Co2(2))+Co2(3);
Fun_array = {
linearFun
powerFun
indexFun
sinFun};
% 设置系数的起始搜索点
startPos = [1,1];
% 待拟合函数的总数
length = size(Fun1_array,1);
% 拟合结果数组
% fitFunResult = zeros(size(Fun1_array));
% CoResult = zeros(size(Fun1_array));
for i = 1:1:length
subplot(length,1,i);
Fun_array{i}
% 使用 nlinfit 函数拟合
CoResult(i) = nlinfit(x,Y,Fun_array{i},startPos);
% 打印结果
disp('nlinfit拟合后的系数矩阵为:');
disp(CoResult(i));
% 画图
hold on;
xmax = max(x);
xmin = min(x);
xnum = 2*length(x)+50;
x = linspace(xmin,xmax,xnum);
Fun = Fun_array(i);
y = Fun(x,CoResult(i));
plot(x,y,'g');
end
错误警告:
错误使用 nlinfit (第 219 行)
MODELFUN 必须为函数,它返回大小与 Y (5-by-1)相同的拟合值向量。您提供的模型函数返回结果 1-by-2。
大小不匹配的常见原因之一是在函数中使用矩阵运算符(*、/、),而不是对应的元素运算符(.*、./、.)。
然后我就根据这个改
% 被拟合的函数 用于 nlinfit 函数
linearFun = @(x,Co) Co(1)*x+Co(2);
powerFun = @(x,Co) Co(1)*x^Co(2)+Co(3);
indexFun = @(x,Co) Co(1)*exp(Co(2)*x)+Co(3);
sinFun = @(x,Co) Co(1)*sin(x+Co(2))+Co(3);
我改成了这样还是不行
我感觉我跟官方例子根本没有差别……
好吧,或许是参数需要放在参数列表的前面
改成这样,Co 放前面
% 被拟合的函数 用于 nlinfit 函数
linearFun = @(Co,x) Co(1)*x+Co(2);
powerFun = @(Co,x) Co(1)*x^Co(2)+Co(3);
indexFun = @(Co,x) Co(1)*exp(Co(2)*x)+Co(3);
sinFun = @(Co,x) Co(1)*sin(x+Co(2))+Co(3);
现在可以了,但是,嗯,秩亏了
或许是我起始点选得不对
嗯,之后试验过了,盲目选起始点会直接卡死hhh应该是永远都收敛不了
完蛋了,那这样的话其实作为一个循环来说,一点普适性都没有了,还不如单写呢hhh
clc;
% 自变量和应变量
x = [
14.5200
15.2500
15.6000
16.4700
16.9200];
Y = [
116.2000
162.3000
176.1000
251.8000
290.2000];
% 被拟合的函数 用于 nlinfit 函数
linearFun = @(Co,x) Co(1)*x+Co(2);
powerFun = @(Co,x) Co(1)*x^Co(2)+Co(3);
indexFun = @(Co,x) Co(1)*exp(Co(2)*x)+Co(3);
sinFun = @(Co,x) Co(1)*sin(x+Co(2))+Co(3);
Fun_array = {
linearFun
powerFun
indexFun
sinFun};
% 设置系数的起始搜索点
startPos = {
[50,-600]'
[1,2,-100]'
[2,0.25,50]'
[100,0,-100]'};
% 待拟合函数的总数
count = size(Fun_array,1);
for i = 1:1:count
subplot(count,1,i);
% 使用 nlinfit 函数拟合
CoResult = nlinfit(x,Y,Fun_array{i},startPos{i});
% 打印结果
disp('nlinfit拟合后的系数矩阵为:');
disp(CoResult);
% 画图
hold on;
xmax = max(x);
xmin = min(x);
xnum = 2*length(x)+50;
x = linspace(xmin,xmax,xnum);
Fun = Fun_array{i};
y = Fun(CoResult,x);
plot(x,y,'g');
end
接下来再简化,如果直接这样写的话,就会出现求幂的错误
错误使用 nlinfit (第 213 行)
计算模型函数 ‘@(Co,x)Co(1)*x^Co(2)+Co(3)’ 时出错。
原因:
错误使用 ^ (第 51 行)
用于对矩阵求幂的维度不正确。请检查并确保矩阵为方阵并且幂为标量。要执行按元素矩阵求> 幂,请使用 ‘.^’。
如果改成 .^
,又会出现不允许 ^
的错误
错误使用 nlinfit (第 219 行)
MODELFUN 必须为函数,它返回大小与 Y (5-by-1)相同的拟合值向量。您提供的模型函数返回结果 1-by-60。
大小不匹配的常见原因之一是在函数中使用矩阵运算符(*、/、),而不是对应的元素运算符(.*、./、.)。
虽然他这个报错的意思是我不能用 ^
,但是当我把所有运算符都改成元素运算符时,还是不行……我不能理解
最后发现是我自变量数组和匿名函数句柄里面的变量重名了……xs
能正常跑的代码:
clear;
% 自变量和应变量
X = [
14.5200
15.2500
15.6000
16.4700
16.9200];
Y = [
116.2000
162.3000
176.1000
251.8000
290.2000];
% 被拟合的函数 用于 nlinfit 函数
linearFun = @(Co,x) Co(1).*x+Co(2);
powerFun = @(Co,x) Co(1).*x.^Co(2)+Co(3);
indexFun = @(Co,x) Co(1).*exp(Co(2).*x)+Co(3);
sinFun = @(Co,x) Co(1).*sin(x+Co(2))+Co(3);
Fun_array = {
linearFun
powerFun
indexFun
sinFun};
% 设置系数的起始搜索点
startPos = {
[50,-600]'
[1,2,-100]'
[2,0.25,50]'
[100,0,-100]'};
% 待拟合函数的总数
count = size(Fun_array,1);
for i = 1:1:count
subplot(count,1,i);
% 使用 nlinfit 函数拟合
CoResult = nlinfit(X,Y,Fun_array{i},startPos{i});
% 打印结果
disp('nlinfit拟合后的系数矩阵为:');
disp(CoResult);
% 画图
hold on;
xmax = max(X);
xmin = min(X);
xnum = 2*length(X)+50;
x = linspace(xmin,xmax,xnum);
Fun = Fun_array{i};
y = Fun(CoResult,x);
plot(x,y,'g');
end
输出:
nlinfit拟合后的系数矩阵为:
73.0654
-951.6060
警告: 超出迭代限制。将返回最后一次迭代的结果。
nlinfit拟合后的系数矩阵为:
0.0003
4.9155
-39.7506
nlinfit拟合后的系数矩阵为:
3.4509
0.2749
-70.1296
nlinfit拟合后的系数矩阵为:
-90.9788
-0.2107
209.3732