gamultiobj failure when starting with a whole feasible population

8 views (last 30 days)
Hello, I am using gamultiobj of Matlab R2016b only with non-linear constraints. If I try to start the optimisation with a specified initial population which has all the individual feasible, I get the following error:
Assignment has more non-singleton rhs dimensions than non-singleton subscripts
Error in objAndConVectorizer (line 33)
Fvals(i,:) = feval(objFcn,(pop(i,:)));
Error in gamultiobjMakeState (line 118)
[~,C,Ceq,isFeas] =
objAndConVectorizer(state.Population(1:initScoreProvided,:), ...
Error in gamultiobjsolve (line 8)
state =
Error in gamultiobj (line 274)
[x,fval,exitFlag,output,population,scores] = gamultiobjsolve(FitnessFcn,nvars,
Caused by:
Failure in user-supplied fitness function evaluation. Cannot continue.
Instead, if I choose only the first individual of my initial population such that it is infeasible, the optimisation runs with no problem (thus fitness function has no problem). Unfortunately this is an issue when I want to start a new optimisation using the last population of the previous run, to keep on iterating, because I am forced to drop a good individual and to replace the first entry of the population with an infeasible element. If I do not use non-linear constraint, this problem does not occur, even this the error attributes the failure to the fitness function. I have been using a variety of fitness and non-linear constraint functions and I have had this error in all the cases. The way I call the optimiser is standard:
[x,fval,exitflag,output,population,score] = ...
Thanks for help

Accepted Answer

Steve Grikschat
Steve Grikschat on 27 Nov 2017
From the stack trace, you can see that the solver calls the fitness function with a row vector. It should be a 1-by-nvars vector (you could check to be sure). The result of that evaluation is not a vector, but a matrix (or possibly an N-D array), which results in an error.
See this example code that mimics the error code in the stack:
popSize = 4; numObj = 2;
Fvals = Inf(popSize,numObj);
Fvals(2,:) = rand(2,2)
This is likely because of a mismatch in dimensionality between what your fitness function returns and what the solver expects. The solver always requires a vector of function values. The fitness function may not be consistent in how it outputs the results.
If you call your fitness function with the first row of the feasible initial population, what size is the output? What about with the infeasible member (as a row)?
gamultiobj must determine some of the sizes from the input arrays at run-time. Therefore, it can derive numbers that differ from what you expect. Also note that the 1st individual (row) is used for many of the validation checks on the function. So, I wonder if the solver would still error if you put the 1 infeasible point in the middle of the population.
It might also help determine the other behaviors if you could give the other parameters:
  • The size of the InitialPopulation
  • The options.PopulationSize value
  • Number of variables (the 2nd input)
  • CreationFcn
Steve Grikschat
Steve Grikschat on 4 Dec 2017
I can verify that there was a bug in that portion of the code which was fixed in R2017a.
The bug was in the line
fakeFitness = @(x) NaN(numObj,size(x,2));
The 2nd argument to size should be "1".
The reason that the 1st member of the population matters here is that this block of code is only used to evaluate the constraints on the part of the population with the initial score provided (aka, the index "initScoreProvided" which is 1).
The way gamultiobj handles evaluations with nonlinear constraints is to evaluate the constraints first, and then evaluate the objective only if it is feasible.
So, when the 1st member is infeasible, this fakeFitness eval is skipped.
Sorry for the confusion and the error. Again, this is fixed in R2017a and later.

Sign in to comment.

More Answers (0)

Community Treasure Hunt

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

Start Hunting!