Why does this code give me an error?
3 visualizaciones (últimos 30 días)
Mostrar comentarios más antiguos
I want to run the Wild Horse Optimizer (WHO) with my fitness function. It will give me an estimated solution "gBest". Then I want to supply that estimated solution to the local builtin optimizer "sqp" while providing an initial guess as a starting point. My code is below:
clear;clc
u=[-33 33];% desired vector
dim=length(u);
lb=-90*ones(1,dim);
ub= 90*ones(1,dim);
Noise=0;
% Define the objective function
objectiveFunctionForMetaheuristic = @(x) MIMOfunNoise(x,u,Noise) + penaltyTerm(x, u);
objectiveFunctionForLocal = @(x) MIMOfunNoise(x, u, Noise) + penaltyTerm(x, u);
% Initial guess
initialGuess = u;
% Set options for fmincon (SQP solver)
options = optimoptions('fmincon', 'Algorithm', 'sqp', 'Display', 'off');
Runs=30;
% Pre-allocation for WHO algorithm
one=zeros(Runs,1);
time=zeros(Runs,1);
temp=zeros(Runs,dim);
two=zeros(Runs,dim);
% Pre-allocation for SQP algorithm
oneSQP=zeros(Runs,1);
timeSQP=zeros(Runs,1);
tempSQP=zeros(Runs,dim);
twoSQP=zeros(Runs,dim);
nn=0;
for n=1:Runs %------------(2)
nn=nn+1;
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% Call WHO
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%[time,gBest,gBestScore]=WHO(N,Max_iter,lb,ub,dim,objectiveFunction);
[time,gBest,gBestScore]=WHO(30,500,lb,ub,dim,objectiveFunctionForMetaheuristic);
one(nn)=gBestScore;
temp(nn,:)=gBest;
time1(nn)=time;
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%- Swapping
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
[~, ix] = sort(u);
[~, ix1(ix)] = sort(temp(nn,:));
two(nn,:) = temp(nn,ix1);
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% Call the SQP
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
tic;
%[bestX, fmin] = fmincon(objectiveFunctionForLocal, gBest, [], [], [], [], lb, ub, [], options);
objectiveFunctionForLocal(gBest)
[c,ceq] = nonlinear_constraint(gBest)
[bestX, fmin] = fmincon(objectiveFunctionForLocal, gBest, [], [], [], [], lb, ub, @(x) nonlinear_constraint(x), options, initialGuess);
timeSQP(nn)=toc;
oneSQP(nn)=fmin;
tempSQP(nn,:)=bestX;
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%- Swapping
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
[~, ix] = sort(u); % u is my desired vector
[~, ix1(ix)] = sort(tempSQP(nn,:));
twoSQP(nn,:) = tempSQP(nn,ix1);
end
%%%%%%%%%%%%%%%%%%%
% Choose best
%%%%%%%%%%%%%%%%%%%
[one1 ind]=sort(one,'descend');
[fitness,ind1]=min(one1);
two1=two(ind1,:);
[one1SQP indSQP]=sort(oneSQP','descend');
[fitnessSQP,ind1SQP]=min(one1SQP);
two1SQP=twoSQP(ind1SQP,:);
% Display results
format compact
fprintf('Global_Sol : %s\n', num2str(round(two1, 4),'%.4f '));
fprintf('Local_Sol : %s\n', num2str(round(two1SQP,4),'%.4f '));
fprintf('Desired : %s\n', num2str(u,'%.4f '));
fprintf('Global_fmin : %f\n', fitness);
fprintf('Local_fmin : %f\n', fitnessSQP);
%%%%%%%%%%%%%%%%%%
% Save workspace data
%%%%%%%%%%%%%%%%%
%save 2sn0dB
function e=MIMOfunNoise(b,u,Noise)
M=6; % const1
N=6; % const2
K=length(u);%const3
d = 0.5; % const4
vec = @(MAT) MAT(:);
vecH = @(MAT) MAT(:).';
steerVecT = @(ang) exp(1j*2*pi*d*(0:M-1).'*sin(vecH(ang)));
steerVecR = @(ang) exp(1j*2*pi*d*(0:N-1).'*sin(vecH(ang)));
%%%%%%%%%%%%%%%%%%%%
% Swapping vector b
%%%%%%%%%%%%%%%%%%%%
[~, ix] = sort(u);
[~, ix1(ix)] = sort(b);
b = b(ix1);
A = ones(K, 1);
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% Calculation of yo and ye
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
yo = yMatTR(deg2rad(u), steerVecT, steerVecR);
yo=awgn(yo,Noise);
ye = yMatTR(deg2rad(b), steerVecT, steerVecR);
%%%%%%%%%%%%%%%%%%
% MSE
%%%%%%%%%%%%%%%%%%
e=norm(yo-ye).^2/(M*N);
end
%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% User defined function called within MIMOfunNoise
%%%%%%%%%%%%%%%%%%%%%%%%5%%%
function y = yMatTR(targetAngle, steerVecT, steerVecR)
steerA = steerVecT(targetAngle);
steerB = steerVecR(targetAngle);
y=sum( steerA.*permute(steerB,[3,2,1]) ,2);
y=y(:);
end
function penalty = penaltyTerm(x, desiredResult)
% Define a penalty term based on the deviation from the desired result
penalty = 100 * sum((x - desiredResult).^2);
end
function [X]=initialization(N,dim,up,down)
if size(up,1)==1
X=rand(N,dim).*(up-down)+down;
end
if size(up,1)>1
for i=1:dim
high=up(i);low=down(i);
X(:,i)=rand(1,N).*(high-low)+low;
end
end
end
function Stallion=exchange(Stallion)
nStallion=length(Stallion);
for i=1:nStallion
[value,index]=min([Stallion(i).group.cost]);
if value<Stallion(i).cost
bestgroup=Stallion(i).group(index);
Stallion(i).group(index).pos=Stallion(i).pos;
Stallion(i).group(index).cost=Stallion(i).cost;
Stallion(i).pos=bestgroup.pos;
Stallion(i).cost=bestgroup.cost;
end
end
end
% Developed in MATLAB R2017b
% Source codes demo version 1.0
% _____________________________________________________
% Author, inventor and programmer: Iraj Naruei and Farshid Keynia,
% e-Mail: irajnaruei@iauk.ac.ir , irajnaruei@yahoo.com
% _____________________________________________________
% Co-author and Advisor: Farshid Keynia
%
% e-Mail: fkeynia@gmail.com
% _____________________________________________________
% Co-authors: Amir Sabbagh Molahoseyni
%
% e-Mail: sabbagh@iauk.ac.ir
% _____________________________________________________
% You can find the Wild Horse Optimizer code at
% _____________________________________________________
%% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% Max_iter: maximum iterations, N: populatoin size, Convergence_curve: Convergence curve
%function [Convergence_curve,gBest,gBestScore]=WHO(N,Max_iter,lb,ub,dim,fobj)
function [time,gBest,gBestScore]=WHO(N,Max_iter,lb,ub,dim,fobj)
tic; % By Me
if size(ub,1)==1
ub=ones(1,dim).*ub;
lb=ones(1,dim).*lb;
end
PS=0.2; % Stallions Percentage
PC=0.13; % Crossover Percentage
NStallion=ceil(PS*N); % number Stallion
Nfoal=N-NStallion;
Convergence_curve = zeros(1,Max_iter);
gBest=zeros(1,dim);
gBestScore=inf;
%create initial population
empty.pos=[];
empty.cost=[];
group=repmat(empty,Nfoal,1);
for i=1:Nfoal
group(i).pos=lb+rand(1,dim).*(ub-lb);
group(i).cost=fobj(group(i).pos);
end
Stallion=repmat(empty,NStallion,1);
for i=1:NStallion
Stallion(i).pos=lb+rand(1,dim).*(ub-lb);
Stallion(i).cost=fobj(Stallion(i).pos);
end
ngroup=length(group);
a=randperm(ngroup);
group=group(a);
i=0;
k=1;
for j=1:ngroup
i=i+1;
Stallion(i).group(k)=group(j);
if i==NStallion
i=0;
k=k+1;
end
end
Stallion=exchange(Stallion);
[value,index]=min([Stallion.cost]);
WH=Stallion(index); % global
gBest=WH.pos;
gBestScore=WH.cost;
Convergence_curve(1)=WH.cost;
l=2; % Loop counter
while l<Max_iter+1
TDR=1-l*((1)/Max_iter);
for i=1:NStallion
ngroup=length(Stallion(i).group);
[~,index]=sort([Stallion(i).group.cost]);
Stallion(i).group=Stallion(i).group(index);
for j=1:ngroup
if rand>PC
z=rand(1,dim)<TDR;
r1=rand;
r2=rand(1,dim);
idx=(z==0);
r3=r1.*idx+r2.*~idx;
rr=-2+4*r3;
Stallion(i).group(j).pos= 2*r3.*cos(2*pi*rr).*(Stallion(i).pos-Stallion(i).group(j).pos)+(Stallion(i).pos);
else
A=randperm(NStallion);
A(A==i)=[];
a=A(1);
c=A(2);
% B=randperm(ngroup);
% BB=randperm(ngroup);
% b1=B(1);b2=BB(1);
x1=Stallion(c).group(end).pos;
x2=Stallion(a).group(end).pos;
y1=(x1+x2)/2; % Crossover
Stallion(i).group(j).pos=y1;
end
Stallion(i).group(j).pos=min(Stallion(i).group(j).pos,ub);
Stallion(i).group(j).pos=max(Stallion(i).group(j).pos,lb);
Stallion(i).group(j).cost=fobj(Stallion(i).group(j).pos);
end
% end
%
% for i=1:NStallion
R=rand;
% z=rand(1,dim)<TDR;
% r1=rand;
% r2=rand(1,dim);
% idx=(z==0);
% r3=r1.*idx+r2.*~idx;
% rr=-2+4*r3;
if R<0.5
k= 2*r3.*cos(2*pi*rr).*(WH.pos-(Stallion(i).pos))+WH.pos;
else
k= 2*r3.*cos(2*pi*rr).*(WH.pos-(Stallion(i).pos))-WH.pos;
end
k=min(k,ub);
k=max(k,lb);
fk=fobj(k);
if fk<Stallion(i).cost
Stallion(i).pos =k;
Stallion(i).cost=fk;
end
end
Stallion=exchange(Stallion);
[value,index]=min([Stallion.cost]);
if value<WH.cost
WH=Stallion(index);
end
gBest=WH.pos;
gBestScore=WH.cost;
Convergence_curve(l)=WH.cost;
l = l + 1;
time=toc; % By Me
end
end
The WHO and its supported files are in the attachment. But when I run the above code, it gives me an error like this:
Error using abcd>@(x)MIMOfunNoise(x,u,Noise)+penaltyTerm(x,u)
Too many input arguments.
Error in fmincon (line 563)
initVals.f = feval(funfcn{3},X,varargin{:});
Error in abcd (line 61)
[bestX, fmin] = fmincon(objectiveFunctionForLocal, gBest, [], [], [], [], lb, ub, @(x) nonlinear_constraint(x), options, initialGuess);
Caused by:
Failure in initial objective function evaluation. FMINCON
cannot continue.
>>
8 comentarios
Sam Chak
el 24 de Feb. de 2024
@Sadiq Akbar, you should check and compare the fmincon() function in your code with the proper syntax of fmincon as shown below:
[bestX, fmin] = fmincon(objectiveFunctionForLocal, ... % cost function
gBest, ... % initial point
[], ... % A
[], ... % b
[], ... % Aeq
[], ... % beq
lb, ... % lower bound
ub, ... % upper bound
@(x) nonlinear_constraint(x), ... % nonlinear inequalities
options, ... % optimoptions()
initialGuess); % ???
Respuestas (2)
Sam Chak
el 24 de Feb. de 2024
Hi @Sadiq Akbar
If nonlinear inequality constraints are not available, you can disable them in the code. It appears that the updated code now returns some results. Please verify and check.
% [c,ceq] = nonlinear_constraint(gBest)
[bestX, fmin] = fmincon(objectiveFunctionForLocal, gBest, [], [], [], [], lb, ub, [], options)
%%%%%%%%%%%%%%%%%%%
% Choose best
%%%%%%%%%%%%%%%%%%%
[one1 ind]=sort(one,'descend');
[fitness,ind1]=min(one1);
two1=two(ind1,:);
[one1SQP indSQP]=sort(oneSQP','descend');
[fitnessSQP,ind1SQP]=min(one1SQP);
two1SQP=twoSQP(ind1SQP,:);
% Display results
format compact
fprintf('Global_Sol : %s\n', num2str(round(two1, 4),'%.4f '));
fprintf('Local_Sol : %s\n', num2str(round(two1SQP,4),'%.4f '));
fprintf('Desired : %s\n', num2str(u,'%.4f '));
fprintf('Global_fmin : %f\n', fitness);
fprintf('Local_fmin : %f\n', fitnessSQP);
2 comentarios
Sam Chak
el 24 de Feb. de 2024
You're welcome, @Sadiq Akbar. I simply fixed the fmincon syntax in the optimization code to get it running. As for why the GA-SQP hybrid is expected to perform better in your problem, I cannot provide a definitive answer at the moment.
Walter Roberson
el 24 de Feb. de 2024
[bestX, fmin] = fmincon(objectiveFunctionForLocal, gBest, [], [], [], [], lb, ub, @(x) nonlinear_constraint(x), options, initialGuess);
fmincon() does not expect an initialGuess parameter. It sees the initialGuess as an extra parameter. What it does with that extra parameter is no longer documented: it passes that extra parameter as an extra parameter to objectiveFunctionForLocal and as an extra parameter to @(x) nonlinear_constraint(x) too. But
objectiveFunctionForLocal = @(x) MIMOfunNoise(x, u, Noise) + penaltyTerm(x, u);
expects only a single parameter, and so gives an error when the extra parameter intialGuess is passed to it.
Ver también
Categorías
Más información sobre Solver Outputs and Iterative Display en Help Center y File Exchange.
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!