LCOV - code coverage report
Current view: top level - ves - Optimizer.h (source / functions) Hit Total Coverage
Test: plumed test coverage Lines: 53 57 93.0 %
Date: 2025-03-25 09:33:27 Functions: 9 10 90.0 %

          Line data    Source code
       1             : /* +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
       2             :    Copyright (c) 2016-2021 The VES code team
       3             :    (see the PEOPLE-VES file at the root of this folder for a list of names)
       4             : 
       5             :    See http://www.ves-code.org for more information.
       6             : 
       7             :    This file is part of VES code module.
       8             : 
       9             :    The VES code module is free software: you can redistribute it and/or modify
      10             :    it under the terms of the GNU Lesser General Public License as published by
      11             :    the Free Software Foundation, either version 3 of the License, or
      12             :    (at your option) any later version.
      13             : 
      14             :    The VES code module is distributed in the hope that it will be useful,
      15             :    but WITHOUT ANY WARRANTY; without even the implied warranty of
      16             :    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      17             :    GNU Lesser General Public License for more details.
      18             : 
      19             :    You should have received a copy of the GNU Lesser General Public License
      20             :    along with the VES code module.  If not, see <http://www.gnu.org/licenses/>.
      21             : +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ */
      22             : #ifndef __PLUMED_ves_Optimizer_h
      23             : #define __PLUMED_ves_Optimizer_h
      24             : 
      25             : #include "VesBias.h"
      26             : 
      27             : #include "core/ActionPilot.h"
      28             : #include "core/ActionWithValue.h"
      29             : 
      30             : #include <vector>
      31             : #include <string>
      32             : #include <cmath>
      33             : #include <memory>
      34             : 
      35             : 
      36             : #define PLUMED_VES_OPTIMIZER_INIT(ao) Action(ao),Optimizer(ao)
      37             : 
      38             : namespace PLMD {
      39             : 
      40             : /**
      41             : \ingroup INHERIT
      42             : Abstract base class for implenting new optimization methods
      43             : */
      44             : 
      45             : class OFile;
      46             : 
      47             : namespace ves {
      48             : 
      49             : class CoeffsVector;
      50             : class VesBias;
      51             : 
      52             : 
      53             : class Optimizer :
      54             :   public ActionPilot,
      55             :   public ActionWithValue {
      56             : private:
      57             :   const std::string description_;
      58             :   const std::string type_;
      59             :   //
      60             :   std::vector<double> stepsizes_;
      61             :   std::vector<double> current_stepsizes;
      62             :   bool fixed_stepsize_;
      63             :   //
      64             :   unsigned int iter_counter;
      65             :   //
      66             :   bool use_hessian_;
      67             :   bool diagonal_hessian_;
      68             :   bool hessian_covariance_from_averages_;
      69             :   //
      70             :   bool monitor_instantaneous_gradient_;
      71             :   //
      72             :   bool use_mwalkers_mpi_;
      73             :   bool mwalkers_mpi_single_files_;
      74             :   //
      75             :   std::vector<bool> dynamic_targetdists_;
      76             :   unsigned int ustride_targetdist_;
      77             :   //
      78             :   unsigned int ustride_reweightfactor_;
      79             :   //
      80             :   std::string coeffssetid_prefix_;
      81             :   //
      82             :   unsigned int coeffs_wstride_;
      83             :   std::vector<std::unique_ptr<OFile>> coeffsOFiles_;
      84             :   std::string coeffs_output_fmt_;
      85             :   //
      86             :   unsigned int gradient_wstride_;
      87             :   std::vector<std::unique_ptr<OFile>> gradientOFiles_;
      88             :   std::string gradient_output_fmt_;
      89             :   //
      90             :   unsigned int hessian_wstride_;
      91             :   std::vector<std::unique_ptr<OFile>> hessianOFiles_;
      92             :   std::string hessian_output_fmt_;
      93             :   //
      94             :   unsigned int targetdist_averages_wstride_;
      95             :   std::vector<std::unique_ptr<OFile>> targetdist_averagesOFiles_;
      96             :   std::string targetdist_averages_output_fmt_;
      97             :   //
      98             :   unsigned int nbiases_;
      99             :   std::vector<VesBias*> bias_pntrs_;
     100             :   //
     101             :   unsigned int ncoeffssets_;
     102             :   std::vector<CoeffsVector*> coeffs_pntrs_;
     103             :   std::vector<std::unique_ptr<CoeffsVector>> aux_coeffs_pntrs_;
     104             :   std::vector<CoeffsVector*> gradient_pntrs_;
     105             :   std::vector<std::unique_ptr<CoeffsVector>> aver_gradient_pntrs_;
     106             :   std::vector<CoeffsMatrix*> hessian_pntrs_;
     107             :   std::vector<std::unique_ptr<CoeffsVector>> coeffs_mask_pntrs_;
     108             :   std::vector<CoeffsVector*> targetdist_averages_pntrs_;
     109             :   //
     110             :   bool identical_coeffs_shape_;
     111             :   //
     112             :   bool bias_output_active_;
     113             :   unsigned int bias_output_stride_;
     114             :   bool fes_output_active_;
     115             :   unsigned int fes_output_stride_;
     116             :   bool fesproj_output_active_;
     117             :   unsigned int fesproj_output_stride_;
     118             :   bool targetdist_output_active_;
     119             :   unsigned int targetdist_output_stride_;
     120             :   bool targetdist_proj_output_active_;
     121             :   unsigned int targetdist_proj_output_stride_;
     122             :   //
     123             :   bool isFirstStep;
     124             :   //
     125             : private:
     126             :   void updateOutputComponents();
     127             :   void writeOutputFiles(const unsigned int coeffs_id = 0);
     128             :   void readCoeffsFromFiles(const std::vector<std::string>&, const bool);
     129             :   void setAllCoeffsSetIterationCounters();
     130             : protected:
     131             :   void turnOnHessian();
     132             :   void turnOffHessian();
     133             :   std::vector<CoeffsMatrix*> enableHessian(VesBias*, const bool diagonal_hessian=false);
     134             :   // CoeffsMatrix* switchToDiagonalHessian(VesBias*);
     135             :   // CoeffsMatrix* switchToFullHessian(VesBias*);
     136             :   //
     137             :   CoeffsVector& Coeffs(const unsigned int coeffs_id = 0) const;
     138             :   CoeffsVector& AuxCoeffs(const unsigned int coeffs_id = 0) const;
     139             :   CoeffsVector& Gradient(const unsigned int coeffs_id = 0) const;
     140             :   CoeffsMatrix& Hessian(const unsigned int coeffs_id = 0) const;
     141             :   CoeffsVector& CoeffsMask(const unsigned int coeffs_id = 0) const;
     142             :   CoeffsVector& TargetDistAverages(const unsigned int coeffs_id = 0) const;
     143             :   double StepSize(const unsigned int coeffs_id = 0) const;
     144             :   virtual void coeffsUpdate(const unsigned int coeffs_id = 0) = 0;
     145             :   void setCurrentStepSize(const double,const unsigned int i = 0);
     146             :   void setCurrentStepSizes(const std::vector<double>&);
     147             :   //
     148             :   void turnOffCoeffsOutputFiles();
     149             :   //
     150             :   template<class T>
     151             :   bool parseMultipleValues(const std::string&, std::vector<T>&);
     152             :   template<class T>
     153             :   bool parseMultipleValues(const std::string&, std::vector<T>&, const T&);
     154             :   void parseFilenames(const std::string&, std::vector<std::string>&, const std::string&);
     155             :   void parseFilenames(const std::string&, std::vector<std::string>&);
     156             :   void addCoeffsSetIDsToFilenames(std::vector<std::string>&, std::string&);
     157             :   void setupOFiles(std::vector<std::string>&, std::vector<std::unique_ptr<OFile>>&, const bool multi_sim_single_files=false);
     158             : public:
     159             :   static void registerKeywords(Keywords&);
     160             :   static void useMultipleWalkersKeywords(Keywords&);
     161             :   static void useHessianKeywords(Keywords&);
     162             :   static void useFixedStepSizeKeywords(Keywords&);
     163             :   static void useDynamicStepSizeKeywords(Keywords&);
     164             :   static void useMaskKeywords(Keywords&);
     165             :   static void useRestartKeywords(Keywords&);
     166             :   static void useMonitorAverageGradientKeywords(Keywords&);
     167             :   static void useDynamicTargetDistributionKeywords(Keywords&);
     168             :   static void useReweightFactorKeywords(Keywords&);
     169             :   //
     170             :   explicit Optimizer(const ActionOptions&ao);
     171             :   ~Optimizer();
     172             :   std::string getType() const {
     173             :     return type_;
     174             :   }
     175             :   std::string getDescription() const {
     176             :     return description_;
     177             :   }
     178             :   //
     179             :   unsigned int numberOfBiases() const {
     180             :     return nbiases_;
     181             :   }
     182             :   unsigned int numberOfCoeffsSets() const {
     183          16 :     return ncoeffssets_;
     184             :   }
     185             :   //
     186             :   std::vector<double> getStepSizes() const;
     187             :   std::vector<double> getCurrentStepSizes() const;
     188             :   double getStepSize(const unsigned int coeffs_id = 0) const;
     189             :   double getCurrentStepSize(const unsigned int coeffs_id = 0) const;
     190             :   void setStepSizes(const std::vector<double>&);
     191             :   void setStepSize(const double, const unsigned int coeffs_id = 0);
     192             :   //
     193             :   unsigned int getIterationCounter() const;
     194             :   double getIterationCounterDbl() const;
     195             :   std::string getIterationCounterStr(const int offset=0) const;
     196             :   void setIterationCounter(const unsigned int);
     197             :   void increaseIterationCounter();
     198             :   //
     199       22879 :   void apply() override {};
     200       22879 :   void calculate() override {};
     201             :   void update() override;
     202           0 :   unsigned int getNumberOfDerivatives() override {
     203           0 :     return 0;
     204             :   }
     205             :   //
     206             :   bool fixedStepSize() const {
     207             :     return fixed_stepsize_;
     208             :   }
     209             :   bool dynamicStepSize() const {
     210             :     return !fixed_stepsize_;
     211             :   }
     212             :   //
     213             :   bool useHessian() const {
     214             :     return use_hessian_;
     215             :   }
     216             :   bool diagonalHessian() const {
     217             :     return diagonal_hessian_;
     218             :   }
     219             :   //
     220             :   bool useMultipleWalkers() const {
     221         609 :     return use_mwalkers_mpi_;
     222             :   }
     223             :   //
     224             :   std::vector<VesBias*> getBiasPntrs() const {
     225             :     return bias_pntrs_;
     226             :   }
     227             :   std::vector<CoeffsVector*> getCoeffsPntrs() const {
     228             :     return coeffs_pntrs_;
     229             :   }
     230             :   std::vector<CoeffsVector*> getAuxCoeffsPntrs() const {
     231             :     return Tools::unique2raw(aux_coeffs_pntrs_);
     232             :   }
     233             :   std::vector<CoeffsVector*> getGradientPntrs()const {
     234          12 :     return gradient_pntrs_;
     235             :   }
     236             :   std::vector<CoeffsMatrix*> getHessianPntrs() const {
     237             :     return hessian_pntrs_;
     238             :   }
     239             :   std::vector<CoeffsVector*> getCoeffsMaskPntrs() const {
     240             :     return Tools::unique2raw(coeffs_mask_pntrs_);
     241             :   }
     242             :   std::vector<CoeffsVector*> getTargetDistAveragesPntrs() const {
     243             :     return targetdist_averages_pntrs_;
     244             :   }
     245             :   //
     246             :   bool isBiasOutputActive() const {
     247       22829 :     return bias_output_active_;
     248             :   }
     249             :   unsigned int getBiasOutputStride() const {
     250         814 :     return bias_output_stride_;
     251             :   }
     252             :   void setBiasOutputStride(unsigned int stride) {
     253             :     bias_output_stride_=stride;
     254             :   }
     255             :   void writeBiasOutputFiles() const;
     256             :   //
     257             :   bool isFesOutputActive() const {
     258       22829 :     return fes_output_active_;
     259             :   }
     260             :   unsigned int getFesOutputStride() const {
     261         814 :     return fes_output_stride_;
     262             :   }
     263             :   void setFesOutputStride(unsigned int stride) {
     264             :     fes_output_stride_=stride;
     265             :   }
     266             :   void writeFesOutputFiles() const;
     267             :   //
     268             :   bool isFesProjOutputActive() const {
     269       22829 :     return fesproj_output_active_;
     270             :   }
     271             :   unsigned int getFesProjOutputStride() const {
     272         176 :     return fesproj_output_stride_;
     273             :   }
     274             :   void setFesProjOutputStride(unsigned int stride) {
     275             :     fesproj_output_stride_=stride;
     276             :   }
     277             :   void writeFesProjOutputFiles() const;
     278             :   //
     279             :   bool isTargetDistOutputActive() const {
     280       22908 :     return targetdist_output_active_;
     281             :   }
     282             :   unsigned int getTargetDistOutputStride() const {
     283       22367 :     return targetdist_output_stride_;
     284             :   }
     285             :   void setTargetDistOutputStride(unsigned int stride) {
     286             :     targetdist_output_stride_=stride;
     287             :   }
     288             :   void writeTargetDistOutputFiles() const;
     289             :   //
     290             :   bool isTargetDistProjOutputActive() const {
     291       22829 :     return targetdist_proj_output_active_;
     292             :   }
     293             :   unsigned int getTargetDistProjOutputStride() const {
     294          33 :     return targetdist_proj_output_stride_;
     295             :   }
     296             :   void setTargetDistProjOutputStride(unsigned int stride) {
     297             :     targetdist_proj_output_stride_=stride;
     298             :   }
     299             :   void writeTargetDistProjOutputFiles() const;
     300             :   //
     301             : };
     302             : 
     303             : inline
     304             : double Optimizer::StepSize(const unsigned int coeffs_id) const {
     305       22705 :   return stepsizes_[coeffs_id];
     306             : }
     307             : 
     308             : inline
     309             : CoeffsVector& Optimizer::Coeffs(const unsigned int coeffs_id) const {
     310       68214 :   return *coeffs_pntrs_[coeffs_id];
     311             : }
     312             : 
     313             : inline
     314             : CoeffsVector& Optimizer::AuxCoeffs(const unsigned int coeffs_id) const {
     315          21 :   return *aux_coeffs_pntrs_[coeffs_id];
     316             : }
     317             : 
     318             : inline
     319             : CoeffsVector& Optimizer::Gradient(const unsigned int coeffs_id) const {
     320       22785 :   return *gradient_pntrs_[coeffs_id];
     321             : }
     322             : 
     323             : inline
     324       22735 : CoeffsMatrix& Optimizer::Hessian(const unsigned int coeffs_id) const {
     325       22735 :   plumed_massert(use_hessian_,"You cannot use the Hessian without asking for before");
     326       22735 :   return *hessian_pntrs_[coeffs_id];
     327             : }
     328             : 
     329             : inline
     330             : CoeffsVector& Optimizer::CoeffsMask(const unsigned int coeffs_id) const {
     331             :   return *coeffs_mask_pntrs_[coeffs_id];
     332             : }
     333             : 
     334             : inline
     335             : std::vector<double> Optimizer::getStepSizes() const {
     336             :   return stepsizes_;
     337             : }
     338             : 
     339             : inline
     340             : std::vector<double> Optimizer::getCurrentStepSizes() const {
     341             :   return current_stepsizes;
     342             : }
     343             : 
     344             : inline
     345             : double Optimizer::getStepSize(const unsigned int coeffs_id) const {
     346             :   return stepsizes_[coeffs_id];
     347             : }
     348             : 
     349             : inline
     350             : double Optimizer::getCurrentStepSize(const unsigned int coeffs_id) const {
     351          11 :   return current_stepsizes[coeffs_id];
     352             : }
     353             : 
     354             : inline
     355             : void Optimizer::setStepSizes(const std::vector<double>& stepsizes_in) {
     356             :   plumed_assert(stepsizes_in.size()==ncoeffssets_);
     357             :   stepsizes_ = stepsizes_in;
     358             : }
     359             : 
     360             : inline
     361             : void Optimizer::setStepSize(const double stepsize_in, const unsigned int coeffs_id) {
     362             :   stepsizes_[coeffs_id] = stepsize_in;
     363             : }
     364             : 
     365             : inline
     366             : void Optimizer::setCurrentStepSize(const double current_stepsize_in, const unsigned int coeffs_id) {
     367          10 :   current_stepsizes[coeffs_id] = current_stepsize_in;
     368             : }
     369             : 
     370             : inline
     371          78 : void Optimizer::setCurrentStepSizes(const std::vector<double>& current_stepsizes_in) {
     372          78 :   plumed_assert(current_stepsizes_in.size()==ncoeffssets_);
     373          78 :   current_stepsizes = current_stepsizes_in;
     374          78 : }
     375             : 
     376             : inline
     377             : unsigned int Optimizer::getIterationCounter() const {
     378       48388 :   return iter_counter;
     379             : }
     380             : 
     381             : inline
     382             : double Optimizer::getIterationCounterDbl() const {
     383       22695 :   return static_cast<double>(iter_counter);
     384             : }
     385             : 
     386             : inline
     387             : void Optimizer::increaseIterationCounter() {
     388       22750 :   iter_counter++;
     389             : }
     390             : 
     391             : inline
     392             : void Optimizer::setIterationCounter(const unsigned int iter_counter_in) {
     393          13 :   iter_counter = iter_counter_in;
     394             : }
     395             : 
     396             : 
     397             : template<class T>
     398         623 : bool Optimizer::parseMultipleValues(const std::string& keyword, std::vector<T>& values) {
     399         623 :   plumed_assert(ncoeffssets_>0);
     400         623 :   plumed_assert(values.size()==0);
     401             :   bool identical_values=false;
     402             :   //
     403         623 :   parseVector(keyword,values);
     404         623 :   if(values.size()==1 && ncoeffssets_>1) {
     405           9 :     values.resize(ncoeffssets_,values[0]);
     406             :     identical_values=true;
     407             :   }
     408         623 :   if(values.size()>0 && values.size()!=ncoeffssets_) {
     409             :     std::string s1;
     410           0 :     Tools::convert(ncoeffssets_,s1);
     411           0 :     plumed_merror("Error in " + keyword + " keyword: either give 1 common value for all coefficient sets or " + s1 + " separate value for each set");
     412             :   }
     413         623 :   return identical_values;
     414             : }
     415             : 
     416             : template<class T>
     417         158 : bool Optimizer::parseMultipleValues(const std::string& keyword, std::vector<T>& values, const T& default_value) {
     418         158 :   bool identical_values = parseMultipleValues(keyword,values);
     419         158 :   if(values.size()==0) {
     420          79 :     values.resize(ncoeffssets_,default_value);
     421             :     identical_values=true;
     422             :   }
     423         158 :   return identical_values;
     424             : }
     425             : 
     426             : inline
     427         158 : void Optimizer::parseFilenames(const std::string& keyword, std::vector<std::string>& fnames, const std::string& default_fname) {
     428         158 :   if(parseMultipleValues<std::string>(keyword,fnames,default_fname)) {
     429          81 :     addCoeffsSetIDsToFilenames(fnames,coeffssetid_prefix_);
     430             :   }
     431         158 : }
     432             : 
     433             : inline
     434         387 : void Optimizer::parseFilenames(const std::string& keyword, std::vector<std::string>& fnames) {
     435         387 :   if(parseMultipleValues<std::string>(keyword,fnames)) {
     436           4 :     addCoeffsSetIDsToFilenames(fnames,coeffssetid_prefix_);
     437             :   }
     438         387 : }
     439             : 
     440             : 
     441             : }
     442             : }
     443             : 
     444             : #endif

Generated by: LCOV version 1.16