/// <summary>
        /// Constructor.
        /// Creates a new multiobjective problem instance.
        /// </summary>
        /// <param name="solutionType">The solution type must "Real" or "BinaryReal", and "ArrayReal".</param>
        /// <param name="numberOfVariables">Number of variables</param>
        public NSGAIIProblem(string solutionType, MOO comp, int solutionsCounter)
        {
            this.component      = comp;
            NumberOfVariables   = comp.readSlidersList().Count;
            NumberOfObjectives  = comp.objectives.Count;
            NumberOfConstraints = 0;
            ProblemName         = "Multiobjective";

            // Log
            comp.LogAddMessage("Number of Variables = " + NumberOfVariables);
            comp.LogAddMessage("Number of Objectives = " + NumberOfObjectives);
            comp.LogAddMessage("Number of Constraints = " + NumberOfConstraints);


            UpperLimit = new double[NumberOfVariables];
            LowerLimit = new double[NumberOfVariables];

            for (int i = 0; i < NumberOfVariables; i++)
            {
                GH_NumberSlider curSlider = comp.readSlidersList()[i];

                LowerLimit[i] = (double)curSlider.Slider.Minimum;
                UpperLimit[i] = (double)curSlider.Slider.Maximum;
            }

            if (solutionType == "BinaryReal")
            {
                SolutionType = new BinaryRealSolutionType(this);
            }
            else if (solutionType == "Real")
            {
                SolutionType = new RealSolutionType(this);
            }
            else if (solutionType == "ArrayReal")
            {
                SolutionType = new ArrayRealSolutionType(this);
            }
            else
            {
                Console.WriteLine("Error: solution type " + solutionType + " is invalid");
                //Logger.Log.Error("Solution type " + solutionType + " is invalid");
                return;
            }

            // Log
            comp.LogAddMessage("Solution Type = " + solutionType);
        }
        /// <summary>
        /// Usage: three options
        ///     - NSGAII
        ///     - NSGAII problemName
        ///     - NSGAII problemName paretoFrontFile
        /// </summary>
        /// <param name="args"></param>
        public NSGAIIRunner(string[] args, Problem p, string Path, MOO comp)
        {
            Problem   problem = p; // The problem to solve
            Algorithm algorithm;   // The algorithm to use
            Operator  crossover;   // Crossover operator
            Operator  mutation;    // Mutation operator
            Operator  selection;   // Selection operator

            this.comp = comp;

            Dictionary <string, object> parameters; // Operator parameters

            QualityIndicator indicators;            // Object to get quality indicators

            // Logger object and file to store log messages
            //var logger = Logger.Log;

            //var appenders = logger.Logger.Repository.GetAppenders();
            //var fileAppender = appenders[0] as log4net.Appender.FileAppender;
            //fileAppender.File = "NSGAII.log";
            //fileAppender.ActivateOptions();

            indicators = null;
            //if (args.Length == 1)
            //{
            //    object[] param = { "Real" };
            //    problem = ProblemFactory.GetProblem(args[0], param);
            //}
            //else if (args.Length == 2)
            //{
            //    object[] param = { "Real" };
            //    problem = ProblemFactory.GetProblem(args[0], param);
            //    indicators = new QualityIndicator(problem, args[1]);
            //}
            //else
            //{ // Default problem
            //    //problem = ;
            //    //problem = new Kursawe("BinaryReal", 3);
            //    //problem = new Water("Real");
            //    //problem = new ZDT3("ArrayReal", 30);
            //    //problem = new ConstrEx("Real");
            //    //problem = new DTLZ1("Real");
            //    //problem = new OKA2("Real") ;
            //}

            algorithm = new NSGAII(problem, comp);
            //algorithm = new ssNSGAII(problem);

            // Algorithm parameters
            algorithm.SetInputParameter("populationSize", comp.popSize);
            algorithm.SetInputParameter("maxEvaluations", comp.maxEvals);
            comp.LogAddMessage("Population Size = " + comp.popSize);
            comp.LogAddMessage("Max Evaluations = " + comp.maxEvals);

            // Mutation and Crossover for Real codification
            parameters = new Dictionary <string, object>();
            parameters.Add("probability", 0.9);
            parameters.Add("distributionIndex", 20.0);
            crossover = CrossoverFactory.GetCrossoverOperator("SBXCrossover", parameters);
            comp.LogAddMessage("Crossover Type = " + "SBXCrossover");
            comp.LogAddMessage("Crossover Probability = " + 0.9);
            comp.LogAddMessage("Crossover Distribution Index = " + 20);

            parameters = new Dictionary <string, object>();
            parameters.Add("probability", 1.0 / problem.NumberOfVariables);
            parameters.Add("distributionIndex", 20.0);
            mutation = MutationFactory.GetMutationOperator("PolynomialMutation", parameters);
            comp.LogAddMessage("Mutation Type = " + "Polynomial Mutation");
            comp.LogAddMessage("Mutation Probability = " + (1 / problem.NumberOfVariables));
            comp.LogAddMessage("Mutation Distribution Index = " + 20);

            // Selection Operator
            parameters = null;
            selection  = SelectionFactory.GetSelectionOperator("BinaryTournament2", parameters);
            comp.LogAddMessage("Selection Type = " + "Binary Tournament 2");

            // Add the operators to the algorithm
            algorithm.AddOperator("crossover", crossover);
            algorithm.AddOperator("mutation", mutation);
            algorithm.AddOperator("selection", selection);

            // Add the indicator object to the algorithm
            algorithm.SetInputParameter("indicators", indicators);

            // Execute the Algorithm
            long        initTime      = Environment.TickCount;
            SolutionSet population    = algorithm.Execute();
            long        estimatedTime = Environment.TickCount - initTime;

            comp.LogAddMessage("Total Execution Time = " + estimatedTime + "ms");

            // Result messages
            //logger.Info("Total execution time: " + estimatedTime + "ms");
            //logger.Info("Variables values have been writen to file VAR");

            //population.PrintVariablesToFile(@"C:\Users\Jonathas\Desktop\text.txt");
            population.PrintVariablesToFile(@"" + comp.fileName + "VAR-" + comp.fileName);
            //logger.Info("Objectives values have been writen to file FUN");
            population.PrintObjectivesToFile(@"" + comp.fileName + "OBJ-" + comp.fileName);
            // Saving all solutions to file


            //Console.WriteLine("Time: " + estimatedTime);
            //Console.ReadLine();
            if (indicators != null)
            {
                //logger.Info("Quality indicators");
                //logger.Info("Hypervolume: " + indicators.GetHypervolume(population));
                //logger.Info("GD         : " + indicators.GetGD(population));
                //logger.Info("IGD        : " + indicators.GetIGD(population));
                //logger.Info("Spread     : " + indicators.GetSpread(population));
                //logger.Info("Epsilon    : " + indicators.GetEpsilon(population));

                int evaluations = (int)algorithm.GetOutputParameter("evaluations");
                //logger.Info("Speed      : " + evaluations + " evaluations");
            }
        }
Esempio n. 3
0
        /// <summary>
        /// Runs the NSGA-II algorithm.
        /// </summary>
        /// <returns>a <code>SolutionSet</code> that is a set of non dominated solutions as a result of the algorithm execution</returns>
        public override SolutionSet Execute()
        {
            // !!!! NEEDED PARAMETES !!! start
            //J* Parameters
            int populationSize = -1; // J* store population size
            int maxEvaluations = -1; // J* store number of max Evaluations
            int evaluations;         // J* number of current evaluations

            // J* Objects needed to illustrate the use of quality indicators inside the algorithms
            QualityIndicator indicators = null; // QualityIndicator object
            int requiredEvaluations;            // Use in the example of use of the
            // indicators object (see below)

            // J* populations needed to implement NSGA-II
            SolutionSet population;          //J* Current population
            SolutionSet offspringPopulation; //J* offspring population
            SolutionSet union;               //J* population resultant from current and offpring population

            //J* Genetic Operators
            Operator mutationOperator;
            Operator crossoverOperator;
            Operator selectionOperator;

            //J* Used to evaluate crowding distance
            Distance distance = new Distance();

            //J* !!!! NEEDED PARAMETES !!! end

            //J* !!! INITIALIZING PARAMETERS - start !!!

            //Read the parameters
            JMetalCSharp.Utils.Utils.GetIntValueFromParameter(this.InputParameters, "maxEvaluations", ref maxEvaluations);  //J* required
            JMetalCSharp.Utils.Utils.GetIntValueFromParameter(this.InputParameters, "populationSize", ref populationSize);  //J* required
            JMetalCSharp.Utils.Utils.GetIndicatorsFromParameters(this.InputParameters, "indicators", ref indicators);       //J* optional

            //Initialize the variables
            population  = new SolutionSet(populationSize);
            evaluations = 0;

            requiredEvaluations = 0;

            //Read the operators
            mutationOperator  = Operators["mutation"];
            crossoverOperator = Operators["crossover"];
            selectionOperator = Operators["selection"];

            //J* !!! INITIALIZING PARAMETERS - end !!!


            //J* !!! Creating first population !!!

            JMetalRandom.SetRandom(comp.MyRand);
            comp.LogAddMessage("Random seed = " + comp.Seed);

            // Create the initial solutionSet
            Solution newSolution;

            for (int i = 0; i < populationSize; i++)
            {
                newSolution = new Solution(Problem);
                Problem.Evaluate(newSolution);
                Problem.EvaluateConstraints(newSolution);
                evaluations++;
                population.Add(newSolution);
            }

            // Generations
            while (evaluations < maxEvaluations)
            {
                // Create the offSpring solutionSet
                offspringPopulation = new SolutionSet(populationSize);
                Solution[] parents = new Solution[2];
                for (int i = 0; i < (populationSize / 2); i++)
                {
                    if (evaluations < maxEvaluations)
                    {
                        //obtain parents
                        parents[0] = (Solution)selectionOperator.Execute(population);
                        parents[1] = (Solution)selectionOperator.Execute(population);
                        Solution[] offSpring = (Solution[])crossoverOperator.Execute(parents);
                        mutationOperator.Execute(offSpring[0]);
                        mutationOperator.Execute(offSpring[1]);
                        Problem.Evaluate(offSpring[0]);
                        Problem.EvaluateConstraints(offSpring[0]);
                        Problem.Evaluate(offSpring[1]);
                        Problem.EvaluateConstraints(offSpring[1]);
                        offspringPopulation.Add(offSpring[0]);
                        offspringPopulation.Add(offSpring[1]);
                        evaluations += 2;
                    }
                }

                // Create the solutionSet union of solutionSet and offSpring
                union = ((SolutionSet)population).Union(offspringPopulation);

                // Ranking the union
                Ranking ranking = new Ranking(union);

                int         remain = populationSize;
                int         index  = 0;
                SolutionSet front  = null;
                population.Clear();

                // Obtain the next front
                front = ranking.GetSubfront(index);

                while ((remain > 0) && (remain >= front.Size()))
                {
                    //Assign crowding distance to individuals
                    distance.CrowdingDistanceAssignment(front, Problem.NumberOfObjectives);
                    //Add the individuals of this front
                    for (int k = 0; k < front.Size(); k++)
                    {
                        population.Add(front.Get(k));
                    }

                    //Decrement remain
                    remain = remain - front.Size();

                    //Obtain the next front
                    index++;
                    if (remain > 0)
                    {
                        front = ranking.GetSubfront(index);
                    }
                }

                // Remain is less than front(index).size, insert only the best one
                if (remain > 0)
                {  // front contains individuals to insert
                    distance.CrowdingDistanceAssignment(front, Problem.NumberOfObjectives);
                    front.Sort(new CrowdingComparator());
                    for (int k = 0; k < remain; k++)
                    {
                        population.Add(front.Get(k));
                    }

                    remain = 0;
                }

                // This piece of code shows how to use the indicator object into the code
                // of NSGA-II. In particular, it finds the number of evaluations required
                // by the algorithm to obtain a Pareto front with a hypervolume higher
                // than the hypervolume of the true Pareto front.
                if ((indicators != null) && (requiredEvaluations == 0))
                {
                    double HV = indicators.GetHypervolume(population);
                    if (HV >= (0.98 * indicators.TrueParetoFrontHypervolume))
                    {
                        requiredEvaluations = evaluations;
                    }
                }
            }



            // Return as output parameter the required evaluations
            SetOutputParameter("evaluations", requiredEvaluations);

            comp.LogAddMessage("Evaluations = " + evaluations);
            // Return the first non-dominated front
            Ranking rank = new Ranking(population);

            Result = rank.GetSubfront(0);

            return(Result);
        }