msu-coinlab / pymop

Single- as well as Multi-Objective Optimization Test Problems: ZDT, DTLZ, CDTLZ, CTP, BNH, OSY, ...
https://www.egr.msu.edu/coinlab/blankjul/pymop/
Apache License 2.0
79 stars 13 forks source link

The constraint is equal to zero #8

Closed ywc1026 closed 5 years ago

ywc1026 commented 5 years ago

What should I do if I have a constraint that equal to zero?

blankjul commented 5 years ago

I had a similar question via E-Mail some time ago. It was about an equality constraint equals to 5.

Equality Constraints are in general challenging to handle using Genetic Algorithms. One way of handling them is see it as a small range.

g(x): x = 5

g'(x): 4.999 <= x <= 5.001  (this can be formulated as two inequality constraints)

Other options of coding it:
g''(x): |x -5| <= 0   or almost the same g'''(x): (x-5)^2 <= 0 

But since the constraint is so strict introducing an epsilon is applied in practice:
g'''(x): (x-5)^2  - eps <= 0

However, all of that is possible I highly recommend using a repair operator. 

The repair operators makes sure all solutions satisfy the equality constraint. An equality constraint often makes most of the design space infeasible.

I am going to add a repair tutorial soon. An example or a repair function for a knapsack problem:

import numpy as np

from pymoo.factory import get_algorithm, get_crossover, get_mutation, get_sampling
from pymoo.model.repair import Repair
from pymoo.optimize import minimize
from pymoo.rand import random
from pymop import create_random_knapsack_problem

class ConsiderMaximumWeightRepair(Repair):

   def _do(self, problem, pop, **kwargs):

       # maximum capacity for the problem
       Q = problem.C

       # the packing plan for the whole population (each row one individual)
       Z = pop.get("X")

       # the corresponding weight of each individual
       weights = (Z * problem.W).sum(axis=1)

       # now repair each indvidiual i
       for i in range(len(Z)):

           # the packing plan for i
           z = Z[i]

           # while the maximum capacity violation holds
           while weights[i] > Q:

               # randomly select an item currently picked
               item_to_remove = random.choice(np.where(z)[0])

               # and remove it
               z[item_to_remove] = False

               # adjust the weight
               weights[i] -= problem.W[item_to_remove]

       # set the design variables for the population
       pop.set("X", Z)
       return pop

method = get_algorithm("ga",
                      pop_size=200,
                      sampling=get_sampling("bin_random"),
                      crossover=get_crossover("bin_hux"),
                      mutation=get_mutation("bin_bitflip"),
                      repair=ConsiderMaximumWeightRepair(),
                      elimate_duplicates=True)

res = minimize(create_random_knapsack_problem(30),
              method,
              termination=('n_gen', 10),
              disp=True)
ywc1026 commented 5 years ago

Thanks for your reply.