lsqcurvefit или lsqnonlinВ этом примере показано, как подогнать функцию к данным с помощью lsqcurvefit вместе с MultiStart. В конце примера показано то же решение с использованием lsqnonlin.
Многие проблемы подгонки имеют несколько локальных решений. MultiStart может помочь найти глобальное решение, что означает наилучшее соответствие. В этом примере сначала используется lsqcurvefit из-за удобного синтаксиса.
Модель:
cx2 + d),
где входные данные x x2), а параметры , , c и d являются неизвестными коэффициентами модели.
Запись анонимной функции, которая принимает матрицу данных xdata с N строки и два столбца и возвращает вектор ответа с N строк. Функция также принимает матрицу коэффициентов p, соответствующий вектору коэффициентов d).
fitfcn = @(p,xdata)p(1) + p(2)*xdata(:,1).*sin(p(3)*xdata(:,2)+p(4));
Создайте 200 точек данных и ответов. Используйте значения 1/2, d = 1. Включить случайный шум в ответ.
rng default % For reproducibility N = 200; % Number of data points preal = [-3,1/4,1/2,1]; % Real coefficients xdata = 5*rand(N,2); % Data points ydata = fitfcn(preal,xdata) + 0.1*randn(N,1); % Response data with noise
Установить границы для lsqcurvefit. Нет причин для того, чтобы d превышал в абсолютном значении, потому что синусоидальная функция принимает значения в своём полном диапазоне на любом интервале ширины . Предположим, что коэффициент должен быть меньше 20 в абсолютном значении, потому что разрешение высокой частоты может вызвать нестабильные отклики или неточную сходимость.
lb = [-Inf,-Inf,-20,-pi]; ub = [Inf,Inf,20,pi];
Установите начальную точку произвольно на (5,5,5,0).
p0 = 5*ones(1,4); % Arbitrary initial point p0(4) = 0; % Ensure the initial point satisfies the bounds
Подгонка параметров к данным, начиная с p0.
[xfitted,errorfitted] = lsqcurvefit(fitfcn,p0,xdata,ydata,lb,ub)
Local minimum possible. lsqcurvefit stopped because the final change in the sum of squares relative to its initial value is less than the value of the function tolerance.
xfitted = 1×4
-2.6149 -0.0238 6.0191 -1.6998
errorfitted = 28.2524
lsqcurvefit находит локальное решение, которое не очень близко к значениям параметров модели (-3,1/4,1/2,1).
MultiStart.Создать структуру проблем так MultiStart может решить ту же проблему.
problem = createOptimProblem('lsqcurvefit','x0',p0,'objective',fitfcn,... 'lb',lb,'ub',ub,'xdata',xdata,'ydata',ydata);
Решить проблему фитинга с помощью MultiStart с 50 итерациями. Постройте график наименьшей ошибки в виде числа MultiStart итерации.
ms = MultiStart('PlotFcns',@gsplotbestf);
[xmulti,errormulti] = run(ms,problem,50)
MultiStart completed the runs from all start points. All 50 local solver runs converged with a positive local solver exit flag.
xmulti = 1×4
-2.9852 -0.2472 -0.4968 -1.0438
errormulti = 1.6464
MultiStart находит глобальное решение вблизи значений параметров (-3, -1/4, -1/2, -1). (Это эквивалентно решению вблизиpreal = (-3,1/4,1/2,1), поскольку изменение знака всех коэффициентов, кроме первого, дает одинаковые числовые значения fitfcn.) Норма остаточной погрешности уменьшается с примерно 28 до примерно 1,6, уменьшаясь более чем в 10 раз.
lsqnonlinДля альтернативного подхода используйте lsqnonlin в качестве функции фитинга. В этом случае в качестве целевой функции используйте разницу между прогнозируемыми значениями и фактическими значениями данных.
fitfcn2 = @(p)fitfcn(p,xdata)-ydata; [xlsqnonlin,errorlsqnonlin] = lsqnonlin(fitfcn2,p0,lb,ub)
Local minimum possible. lsqnonlin stopped because the final change in the sum of squares relative to its initial value is less than the value of the function tolerance.
xlsqnonlin = 1×4
-2.6149 -0.0238 6.0191 -1.6998
errorlsqnonlin = 28.2524
Начиная с той же начальной точки p0, lsqnonlin находит такое же относительно плохое решение, как lsqcurvefit.
Управляемый MultiStart использование lsqnonlin в качестве локального решателя.
problem2 = createOptimProblem('lsqnonlin','x0',p0,'objective',fitfcn2,... 'lb',lb,'ub',ub'); [xmultinonlin,errormultinonlin] = run(ms,problem2,50)

MultiStart completed the runs from all start points. All 50 local solver runs converged with a positive local solver exit flag.
xmultinonlin = 1×4
-2.9852 -0.2472 -0.4968 -1.0438
errormultinonlin = 1.6464
Опять же, MultiStart находит гораздо лучшее решение, чем только локальный решатель.