Optimizer (fminsearch) doesn't work as expected

13 views (last 30 days)
Hi all,
I am working on an optimization problem, where I need to find the global minimum for , where
There is also a constraint or penalty term: .
To test the code, I use the exact solution as the guess, however, the optimizer cannot reproduce the exact solution. And I limit my x to [0, 20] rather than [,], which theoretically affects little.
Some thoughts: My variables are , but is involded in the calculation a lot, I'm wondering whether the calculation of introduces a good amount of errors, which accumulates during the calculation, and affects the results significantly.
The codes are attached below. opt_main.m is the main function and functional_elastic_main.m calculates the objective function to optimize. A figure shows the comparison between the exact solution and the solution produced by the optimizer is attached below as well. Looking at the figure, the optimizer works better for the left-size curve but works not properly for the right-size curve.
No matter what kind of ideas you have, please share those with me. I appreciate very much.
The main function:
function opt_main
%% main function
tic
clear all; clc; close all;
% ---------- user input ----------
% given parameters
mu = 1;
nu = 0.3;
vb = [1,0,0];
b = norm(vb);
lambda = 100; % lagrange multiplier
x = [0:1:20];
% exact solution, used here as input
% it is shifted a bit for better demonstration
del0 = (b/pi*atan(2*(1-nu)*(x-10)/b)+1/2*b);
n = length(x);
% calculate the middle point of x_i and x_i+1
% and dx between x_i and x_i+1
% and length(x1) = n-1;
[x1,dx1] = discrete_x(x);
%% --------------- optimization ---------------
opts = optimset;
opts.TolX = 1e-10;
opts.TolFun = 1e-10;
opts.MaxIter = 1000000;
opts.MaxFunEvals = 1000000;
% ----- perturbation -----
% del0(2:10) = del0(2:10) - 0.1;
objectiveFun = @(d) functional_elastic_main(n,mu,nu,x,x1,dx1,...
d,b,lambda);
[nd2] = fminsearch(objectiveFun,del0,opts);
%% --------------- plotting the results ---------------
plot(x,del0,'--b^','linewidth',2,'MarkerSize',10);
hold on
plot(x,nd2,'-ko','linewidth',2,'MarkerSize',10)
ax = gca;
ax.XAxis.FontSize = 20;
ax.YAxis.FontSize = 20;
xlabel('X','Interpreter','Latex','FontSize',20,'Color','k');
ylabel('$\delta$','Interpreter','Latex','FontSize',25,'Color','k');
legend({'exact','w/ minimization'},'fontsize',16,...
'location','southeast')
print('-dpng','-r400',sprintf('delta_elastic.png'));
%%
toc
fprintf('ALL DONE \n');
end
Objective function:
function [func] = functional_elastic_main(n,mu,nu,x,x1,dx1,del0,b,lambda)
% calculate the middle point of delta_i and delta_i+1
% calculate the slope between delta_i and delta_i+1
[del1,ddeldx1] = discrete_del(del0,x,n);
% ------- calculate U_1 -------
U_1 = 0;
u_1 = zeros(n-1,1);
for ii = 1:n-1
temp1 = -mu/(2*pi*(1-nu))*ddeldx1(ii);
for jj = 1:n-1
if ii ~= jj
temp2 = ddeldx1(jj)*log(abs(x1(ii)-x1(jj)))*dx1(jj);
u_1(ii,1) = u_1(ii,1) + temp1*temp2;
end
end
U_1 = U_1 + u_1(ii,1)*dx1(ii);
end
% ------- calculate U_2 -------
U_2 = 0;
u_2 = zeros(n-1,1);
for ii = 1:n-1
u_2(ii) = mu*b/(4*pi^2)*(1-cos(2*pi*del1(ii)/b));
U_2 = U_2 + u_2(ii)*dx1(ii);
end
% ------- add the contraint or penalty term-------
R = 0;
for ii = 1:n-1
R = R + abs(ddeldx1(ii)*dx1(ii));
end
R = lambda*(R - 1)^2;
func = U_1 + U_2 + R;
end

Accepted Answer

Matt J
Matt J on 30 May 2022
Edited: Matt J on 30 May 2022
It appears that you have 21 unknown variables. That is too many. fminsearch is only guaranteed to converge theoretically for one unknown variable, and empirically starts to perform poorly after about 6 variables.
You might try using ga instead, if you have the Global Optimization Toolbox.
  17 Comments
Joe Zhang
Joe Zhang on 4 Jun 2022
But in my calculation of , is needed and this item dependens on my discretization of x. Also, δis my unknown, but my integrant is integrated over x, which means I need to specify x as unknowns as well, intergal() doesn't work for this case, based on I tested so far. But I think int() can work once I specify x and delta as symbols.
Matt J
Matt J on 4 Jun 2022
Edited: Matt J on 4 Jun 2022
You should probably be parametrizing delta in terms of unknown spline coeffiicients rather than explicit samples. Given the spline coefficients, the continuous-domain derivatives of delta can be obtained by various means, as discussed here,
Once you have continuous-domain derivatives, you can integrate them continuously (with integral()) as well.

Sign in to comment.

More Answers (0)

Products


Release

R2018a

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!