Этот пример показов, как использовать несколько алгоритмов, чтобы решить линейный метод наименьших квадратов задачу с ограниченным ограничением, что решение неотрицательно. Линейный метод наименьших квадратов имеет вид
.
В этом случае ограничьте решение неотрицательным, .
Чтобы начать, загрузите массивы и в рабочую область.
load particle
Просмотрите размер каждого массива.
sizec = size(C)
sizec = 1×2
2000 400
sized = size(d)
sized = 1×2
2000 1
Создайте переменную оптимизации x
соответствующего размера для умножения на C
. Установите нижнюю границу 0
об элементах x
.
x = optimvar('x',sizec(2),'LowerBound',0);
Создайте выражение целевой функции.
residual = C*x - d; obj = sum(residual.^2);
Создайте задачу оптимизации под названием nonneglsq
и включить в задачу целевую функцию.
nonneglsq = optimproblem('Objective',obj);
Найдите решатель по умолчанию для задачи.
opts = optimoptions(nonneglsq)
opts = lsqlin options: Options used by current Algorithm ('interior-point'): (Other available algorithms: 'active-set', 'trust-region-reflective') Set properties: No options set. Default properties: Algorithm: 'interior-point' ConstraintTolerance: 1.0000e-08 Display: 'final' LinearSolver: 'auto' MaxIterations: 200 OptimalityTolerance: 1.0000e-08 StepTolerance: 1.0000e-12 Show options not used by current Algorithm ('interior-point')
Решите задачу с помощью решателя по умолчанию.
[sol,fval,exitflag,output] = solve(nonneglsq);
Solving problem using lsqlin. Minimum found that satisfies the constraints. Optimization completed because the objective function is non-decreasing in feasible directions, to within the value of the optimality tolerance, and constraints are satisfied to within the value of the constraint tolerance.
Чтобы увидеть детали процесса оптимизации, исследуйте структуру output.
disp(output)
message: '...' algorithm: 'interior-point' firstorderopt: 9.9673e-07 constrviolation: 0 iterations: 9 linearsolver: 'sparse' cgiterations: [] solver: 'lsqlin'
Структура output показывает, что lsqlin
решатель использует разреженный внутренний линейный решатель для алгоритма внутренней точки и принимает 9 итераций, чтобы получить меру оптимальности первого порядка около 1e-6.
Алгоритм, отражающий доверительную область, обрабатывает связанные с ограничениями задачи. Посмотрите, насколько хорошо он работает над этой проблемой.
opts.Algorithm = 'trust-region-reflective'; [sol2,fval2,exitflag2,output2] = solve(nonneglsq,'Options',opts);
Solving problem using lsqlin. Local minimum possible. lsqlin stopped because the relative change in function value is less than the function tolerance.
disp(output2)
iterations: 14 algorithm: 'trust-region-reflective' firstorderopt: 5.2187e-08 cgiterations: 54 constrviolation: [] linearsolver: [] message: 'Local minimum possible....' solver: 'lsqlin'
На этот раз решатель принимает больше итераций и приходит к решению с более низкой (лучшей) мерой оптимальности первого порядка.
Чтобы получить еще лучшую меру оптимальности первого порядка, попробуйте задать SubproblemAlgorithm
опция для 'factorization'
.
opts.SubproblemAlgorithm = 'factorization'; [sol3,fval3,exitflag3,output3] = solve(nonneglsq,'Options',opts);
Solving problem using lsqlin. Optimal solution found.
disp(output3)
iterations: 11 algorithm: 'trust-region-reflective' firstorderopt: 1.3973e-14 cgiterations: 0 constrviolation: [] linearsolver: [] message: 'Optimal solution found.' solver: 'lsqlin'
Использование этой опции приводит меру оптимальности первого порядка почти к нулю, что является наилучшим возможным.
The lsqnonneg
решатель специально разработан, чтобы обрабатывать неотрицательную линейную задачу для метода наименьших квадратов. Попробуйте этот решатель.
[sol4,fval4,exitflag4,output4] = solve(nonneglsq,'Solver','lsqnonneg');
Solving problem using lsqnonneg.
disp(output4)
iterations: 184 algorithm: 'active-set' message: 'Optimization terminated.' solver: 'lsqnonneg'
lsqnonneg
не сообщает меру оптимальности первого порядка. Вместо этого исследуйте нормы невязки, которые возвращаются в fval
выходы. Чтобы увидеть цифры более низкой значимости, вычитайте 22.5794 из каждой нормы невязки.
t = table(fval - 22.5794, fval2 - 22.5794, fval3 - 22.5794, fval4 - 22.5794,... 'VariableNames',{'default','trust-region-reflective','factorization','lsqnonneg'})
t=1×4 table
default trust-region-reflective factorization lsqnonneg
__________ _______________________ _____________ __________
5.0804e-05 4.9179e-05 4.9179e-05 4.9179e-05
Решатель по умолчанию имеет несколько более высокую (худшую) норму невязки, чем остальные три, остаточные нормы которых неразличимы на этом уровне точности отображения. Чтобы увидеть, какая из них самая низкая, вычитайте lsqnonneg
результат от двух результатов.
disp([fval2 - fval4,fval3 - fval4])
1.0e-12 * 0.7070 0.6999
The lsqnonneg
норма невязки является наименьшей на почти незначительное количество. Однако lsqnonneg
принимает большинство итераций, чтобы сходиться.