<commit_before>/*-----------------------------------------------------------------------------
 This source file is a part of Hopsan

 Copyright (c) 2009 to present year, Hopsan Group

    This program is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.

    This program is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with this program.  If not, see <http://www.gnu.org/licenses/>.

 For license details and information about the Hopsan Group see the files
 GPLv3 and HOPSANGROUP in the Hopsan source code root directory

 For author and contributor information see the AUTHORS file
-----------------------------------------------------------------------------*/

//!
//! @file   Ops.h
//! @author <NAME> <<EMAIL>>
//! @date   2015-08-31
//!
//! @brief Contains the optimization worker class for the Complex-RF algorithm
//!
//$Id$

#include "OpsWorkerComplexRF.h"
#include "OpsEvaluator.h"
#include "OpsMessageHandler.h"
#include <math.h>
#include <sstream>

using namespace Ops;

WorkerComplexRF::WorkerComplexRF(Evaluator *pEvaluator, MessageHandler *pMessageHandler)
    : WorkerSimplex(pEvaluator, pMessageHandler)
{
    mRetractionCounter = 0;
}

AlgorithmT WorkerComplexRF::getAlgorithm()
{
    return ComplexRF;
}

void WorkerComplexRF::initialize()
{
    WorkerSimplex::initialize();

    mKf = 1.0-pow(mAlpha/2.0, mGamma/mNumPoints);
}

void WorkerComplexRF::run()
{
    mpMessageHandler->printMessage("Running optimization with Complex-RF algorithm.");

    distributePoints();

    mpEvaluator->evaluateAllPoints();

    mpMessageHandler->objectivesChanged();

    calculateBestAndWorstId();

    //Run optimization loop
    mIterationCounter=0;
    for(; mIterationCounter<mnMaxIterations && !mpMessageHandler->aborted(); ++mIterationCounter)
    {
        //Check convergence
        if(checkForConvergence()) break;

        //Increase all objective values (forgetting principle)
        applyForgettingFactor();

        //Calculate best and worst point
        calculateBestAndWorstId();

        //Find geometrical center
        findCentroidPoint();

        //Reflect worst point
        mCandidatePoints[0] = reflect(mPoints[mWorstId], mCentroidPoint, mAlpha);
        mpMessageHandler->candidateChanged(0);
        //std::vector<double> newPoint = mCandidatePoints[0]; //Remember the new point, in case we need to iterate below

        //Evaluate new point
        mpEvaluator->evaluateCandidate(0);
        mPoints[mWorstId] = mCandidatePoints[0];
        mObjectives[mWorstId] = mCandidateObjectives[0];

        mpMessageHandler->pointChanged(mWorstId);
        mpMessageHandler->objectiveChanged(mWorstId);

        calculateBestAndWorstId();

        //Retract until worst point is no longer the same
        mRetractionCounter = 0;
        bool doBreak = false;
        while(mLastWorstId == mWorstId && !mpMessageHandler->aborted())
        {
            ++mIterationCounter;

            mpMessageHandler->stepCompleted(mIterationCounter);

            if(mIterationCounter>=mnMaxIterations)
            {
                --mIterationCounter;    //Needed because for-loop will increase it by one anyway
                break;
            }

            if(retract())
            {
                doBreak = true;
                break;
            }
        }

        if(doBreak)
        {
            break;
        }

        mpMessageHandler->stepCompleted(mIterationCounter);
    }


    if(mpMessageHandler->aborted())
    {
        mpMessageHandler->printMessage("Optimization was aborted after "+std::to_string(mIterationCounter)+" iterations.");
    }
    else if(mIterationCounter == mnMaxIterations)
    {
        mpMessageHandler->printMessage(std::string("Optimization failed to converge after "+std::to_string(mIterationCounter)+" iterations"));
    }
    else
    {
        mpMessageHandler->printMessage("Optimization converged in parameter values after "+std::to_string(mIterationCounter)+" iterations.");
    }

    // Clean up<commit_msg>Fixed numbering of iterations in output from Ops.<commit_after>/*-----------------------------------------------------------------------------
 This source file is a part of Hopsan

 Copyright (c) 2009 to present year, Hopsan Group

    This program is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.

    This program is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with this program.  If not, see <http://www.gnu.org/licenses/>.

 For license details and information about the Hopsan Group see the files
 GPLv3 and HOPSANGROUP in the Hopsan source code root directory

 For author and contributor information see the AUTHORS file
-----------------------------------------------------------------------------*/

//!
//! @file   Ops.h
//! @author <NAME> <<EMAIL>>
//! @date   2015-08-31
//!
//! @brief Contains the optimization worker class for the Complex-RF algorithm
//!
//$Id$

#include "OpsWorkerComplexRF.h"
#include "OpsEvaluator.h"
#include "OpsMessageHandler.h"
#include <math.h>
#include <sstream>

using namespace Ops;

WorkerComplexRF::WorkerComplexRF(Evaluator *pEvaluator, MessageHandler *pMessageHandler)
    : WorkerSimplex(pEvaluator, pMessageHandler)
{
    mRetractionCounter = 0;
}

AlgorithmT WorkerComplexRF::getAlgorithm()
{
    return ComplexRF;
}

void WorkerComplexRF::initialize()
{
    WorkerSimplex::initialize();

    mKf = 1.0-pow(mAlpha/2.0, mGamma/mNumPoints);
}

void WorkerComplexRF::run()
{
    mpMessageHandler->printMessage("Running optimization with Complex-RF algorithm.");

    distributePoints();

    mpEvaluator->evaluateAllPoints();

    mpMessageHandler->objectivesChanged();

    calculateBestAndWorstId();

    //Run optimization loop
    mIterationCounter=0;
    for(; mIterationCounter<mnMaxIterations && !mpMessageHandler->aborted(); ++mIterationCounter)
    {
        //Check convergence
        if(checkForConvergence()) break;

        //Increase all objective values (forgetting principle)
        applyForgettingFactor();

        //Calculate best and worst point
        calculateBestAndWorstId();

        //Find geometrical center
        findCentroidPoint();

        //Reflect worst point
        mCandidatePoints[0] = reflect(mPoints[mWorstId], mCentroidPoint, mAlpha);
        mpMessageHandler->candidateChanged(0);
        //std::vector<double> newPoint = mCandidatePoints[0]; //Remember the new point, in case we need to iterate below

        //Evaluate new point
        mpEvaluator->evaluateCandidate(0);
        mPoints[mWorstId] = mCandidatePoints[0];
        mObjectives[mWorstId] = mCandidateObjectives[0];

        mpMessageHandler->pointChanged(mWorstId);
        mpMessageHandler->objectiveChanged(mWorstId);

        calculateBestAndWorstId();

        mpMessageHandler->stepCompleted(mIterationCounter);

        //Retract until worst point is no longer the same
        mRetractionCounter = 0;
        bool doBreak = false;
        while(mLastWorstId == mWorstId && !mpMessageHandler->aborted())
        {
           // mpMessageHandler->stepCompleted(mIterationCounter);

            ++mIterationCounter;

            mpMessageHandler->stepCompleted(mIterationCounter);

            if(mIterationCounter>=mnMaxIterations)
            {
                --mIterationCounter;    //Needed because for-loop will increase it by one anyway
                break;
            }

            if(retract())
            {
                doBreak = true;
                break;
            }
        }

        if(doBreak)
        {
            break;
        }
    }


    if(mpMessageHandler->aborted())
    {
        mpMessageHandler->printMessage("Optimization was aborted after "+std::to_string(mIterationCounter)+" iterations.");
    }
    else if(mIterationCounter == mnMaxIterations)
    {
        mpMessageHandler->printMessage(std::string("Optimization failed to converge after "+std::to_string(mIterationCounter)+" iterations"));
    }
    else
    {
        mpMessageHandler->printMessage("Optimization converged in parameter values after "+std::to_string(mIterationCounter)+" iterations.");
    }

    // Clean up
{'fraction_non_alphanumeric': 0.12392924685727, 'fraction_numerical': 0.006007342307264434, 'mean_word_length': 2.587390263367917, 'pattern_counts': {'":': 0, '<': 19, '<?xml version=': 0, '>': 50, 'https://': 0, 'lorem ipsum': 0, 'www.': 2, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '7532346', 'n_tokens_mistral': 2499, 'n_tokens_neox': 2354, 'n_words': 677}