QMCPACK
SimpleFixedNodeBranch.h
Go to the documentation of this file.
1 //////////////////////////////////////////////////////////////////////////////////////
2 // This file is distributed under the University of Illinois/NCSA Open Source License.
3 // See LICENSE file in top directory for details.
4 //
5 // Copyright (c) 2019 QMCPACK developers.
6 //
7 // File developed by: Peter Doak, doakpw@ornl.gov, Oak Ridge National Laboratory
8 // Ken Esler, kpesler@gmail.com, University of Illinois at Urbana-Champaign
9 // Jeremy McMinnis, jmcminis@gmail.com, University of Illinois at Urbana-Champaign
10 // Raymond Clay III, j.k.rofling@gmail.com, Lawrence Livermore National Laboratory
11 // Jeongnim Kim, jeongnim.kim@gmail.com, University of Illinois at Urbana-Champaign
12 // Mark A. Berrill, berrillma@ornl.gov, Oak Ridge National Laboratory
13 //
14 // File created by: Jeongnim Kim, jeongnim.kim@gmail.com, University of Illinois at Urbana-Champaign
15 //////////////////////////////////////////////////////////////////////////////////////
16 
17 
18 /**@file SimpleFixedNodeBranch.h
19  * @brief declare a handler of DMC branching
20  *
21  */
22 #ifndef QMCPLUSPLUS_SIMPLE_FIXEDNODE_BRANCHER_H
23 #define QMCPLUSPLUS_SIMPLE_FIXEDNODE_BRANCHER_H
24 
25 #include <array>
26 #include <Configuration.h>
27 #include "OhmmsData/ParameterSet.h"
33 #include "Particle/Walker.h"
34 #include "QMCDrivers/Crowd.h"
35 #include <bitset>
36 
37 namespace qmcplusplus
38 {
39 class WalkerControlBase;
40 class EstimatorManagerBase;
41 
42 /** Manages the state of QMC sections and handles population control for DMCs
43  *
44  * \todo: Remove Estimator dependency, only has come dependency. Express accumulate in
45  * the actual DMC algorithm (i.e. in DMCBatched.cpp)
46  * \todo: Remove duplicate reading of Driver XML section with own copies of input
47  * parameters.
48  * \todo: Rename, it is the only branching class so its name is too much
49  * \todo: Use normal types for data members, don't be clever,
50  * the parameter enums violate KISS and make debugging annoying
51  * \todo: Remove as much state as possible.
52  *
53  * QMCDriver object owns a SimpleFixedNodeBranch to keep track of the
54  * progress of a qmc section. It implements several methods to control the
55  * population and trial energy during a DMC and evaluate the properties of
56  * a population, e.g., energy, variance, population etc.
57  * It owns WalkerController (pointer to a WalkerControlBase object) which
58  * manages the population (killing and duplicating walkers) and
59  * load balancing among multiple MPI tasks.
60  * \see {http://qmcpack.cmscc.org/qmc-basics}
61  *
62  * Steps in 'Legacy' SFNB states machine
63  * 1. Construction (gets global walker number (rank or section wide?)
64  * 2. setEstimatorManager (also makes bootstrapping SFNB state dependent on valid Communicate*)
65  * 3. put(reads driver XML node yet again)
66  * 4. setWalkerController (Maybe a WalkerController pointer is passed in)
67  * 5. InitWalkerController
68  * a. Creates walkercontroller if WalkerController is a nullptr
69  * b. If TargetWalkers isn't known
70  * aa. allreduce and updates MCMW globalWalkers.
71  * bb. resets walker offsets
72  * cc. sets target walkers to whatever current total active walkers is.
73  * c. resets WalkerController
74  * d. If not a restart
75  * aa. saves fixW and killWalker to internal params, otherwise just discards.
76  * bb. updates SFNB copy of MAX/MINWALKRS from walker controller,
77  * these were set in constructer but I guess thats ony if this is a restart
78  * e. setWalkerId
79  * aa. call start()
80  * 1. Which calls reset which crucially calculates and update logN state.
81  * bb. updates all the walker id's of walkers in MCWC.
82  * 6. checkParameters
83  * a. getApproximateEnergyVariance from SFNB's estimator
84  * b. set ETrial, EREF, SIGMA2 from estimator
85  * c. clear EnergyHist and VarianceHist
86  *
87  * Finally branch can be called! It will be called once each step.
88  *
89  * 7. call branch (iter and MCMW)
90  * a. Not first iter during warmup then call WalkerController branch.
91  * else call WC doNotBranch, returns pop_now
92  * b. copy a bunch a state from WC to SFNB (should be with respect to pop_now - number of released nodes)
93  * c. If using taueff update that based on acceptance ration and current tau.
94  * d. If not warmup calculate ETRIAL based on EREF and feedback * log(TargetWalkers) - log(pop_now)
95  * e. set WC's TrialEnergy
96  * d. multiply walkers.Colelctables *= the inverse weight.
97  * f. call SFNB's estimator accumilator on MCWC
98  */
100 {
103 
104  /*! enum for booleans
105  * \since 2008-05-05
106  */
107  enum
108  {
109  B_DMC = 0 /**< 1 for dmc, 0 for anything else */
110  ,
111  B_DMCSTAGE = 1 /**< 1 for main, 0 for wamrup */
112  ,
113  B_POPCONTROL = 2 /**< 1 for the standard dmc, 0 for the comb method */
114  ,
115  B_USETAUEFF = 3 /**< 1 to use taueff accordning to JCP 93, 0 to use tau */
116  ,
117  B_CLEARHISTORY = 4 /**< 1 to clear the history */
118  ,
119  B_KILLNODES = 5 /**< 1 to kill walkers when a node crossing is detected */
120  ,
121  B_RESTART = 6 /**< 1 if restarting */
122  ,
123  B_RMC = 7 /**< 1 for rmc, 0 for anything else */
124  ,
125  B_RMCSTAGE = 8 /**< 1 for main, 0 for warmup */
126  ,
127  B_MODE_MAX = 10 /**< size of BranchMode */
128  };
129 
130  /** booleans to set the branch modes
131  * \since 2008-05-05
132  */
133  using BranchModeType = std::bitset<B_MODE_MAX>;
135 
136  /*! enum for iParam std::bitset<B_IPARAM_MAX>
137  * \since 2008-05-05
138  *
139  * When introducing a new iParam, check if B_IPARAM_MAX is sufficiently large. Use multiples of 8
140  * Why? Much easier to use bool flags. Are these ever serialized?
141  */
142  enum
143  {
144  B_WARMUPSTEPS = 0 /**< warmup steps, valid when BranchMode[D_DMCSTAGE] == 0 */
145  ,
146  B_ENERGYUPDATEINTERVAL = 1 /**< frequency of the trial energy updates, default 1 */
147  ,
148  B_COUNTER = 2 /**< counter for tracking object state */
149  ,
150  B_TARGETWALKERS = 3 /**< target total number of walkers per mpi group */
151  ,
152  B_MAXWALKERS = 4 /**< maximum number of walkers per node */
153  ,
154  B_MINWALKERS = 5 /**< minimum number of walkers per node */
155  ,
156  B_BRANCHINTERVAL = 6 /**< interval between branch, see population control */
157  ,
158  B_IPARAM_MAX = 8 /**< size of iParam */
159  };
160 
161  /** input parameters of integer types
162  * \since 2008-05-05
163  */
166 
167  /** enum for vParam
168  *
169  * Easy serialization is a relatively minor concern compared to the
170  * annoyance this causes elsewhere.
171  */
173  {
174  TAU = 0,
175  TAUEFF,
176  ETRIAL,
177  EREF,
178  ENOW,
179  BRANCHMAX,
180  BRANCHCUTOFF,
181  BRANCHFILTER,
182  SIGMA2,
183  ACC_ENERGY,
184  ACC_SAMPLES,
185  FEEDBACK,
186  FILTERSCALE,
187  VPARAM_MAX = 17 // four extra, why? Sloppy or undocumented hack?
188  };
190 
191  /** controlling parameters of full precision real type
192  *
193  * Mostly internal
194  */
195  template<typename PAR_ENUM>
196  struct VParams : public std::array<FullPrecRealType, static_cast<size_t>(PAR_ENUM::VPARAM_MAX)>
197  {
198  using Base = std::array<FullPrecRealType, static_cast<size_t>(PAR_ENUM::VPARAM_MAX)>;
199  FullPrecRealType& operator[](PAR_ENUM sbvp) { return Base::operator[](static_cast<size_t>(sbvp)); }
200  const FullPrecRealType& operator[](PAR_ENUM sbvp) const { return Base::operator[](static_cast<size_t>(sbvp)); }
201  };
204 
205  /** number of remaning steps for a specific tasks
206  *
207  * set differently for BranchMode[B_DMCSTAGE]
208  */
210  ///Feed*log(N)
212  ///save xml element
213  xmlNodePtr myNode;
214  ///WalkerController
215  std::unique_ptr<WalkerControlBase> WalkerController;
216  ///Backup WalkerController for mixed DMC
217  std::unique_ptr<WalkerControlBase> BackupWalkerController;
218 
219  std::unique_ptr<EstimatorManagerBase> MyEstimator;
220  ///a simple accumulator for energy
222  ///a simple accumulator for variance
224  ///a simple accumulator for energy
226  ///a simple accumulator for energy
228  ///a simple accumulator for reptation's center slice
230  /////histogram of populations
231  //BlockHistogram<RealType> PopHist;
232  /////histogram of populations
233  //BlockHistogram<RealType> DMCEnergyHist;
234  ///root name
235  std::string RootName;
236  ///scheme of branching cutoff
238  ///set of parameters
240  ///string parameters
241  std::vector<std::string> sParam;
242 
243  /// Used for the average scaling
245  unsigned long ScaleNum;
246  //@TODO move these to private
247  ///LogJacob
249  ///LogNorm
250  std::vector<RealType> LogNorm;
251 
252  ///Constructor
253  SimpleFixedNodeBranch(RealType tau, int nideal);
254 
255  ///copy constructor
257 
259 
260  inline bool phaseChanged(RealType psi0) const
261  {
262 // TODO: remove ifdef
263 #if defined(QMC_COMPLEX)
264  return false;
265 #else
266  return std::cos(psi0) < std::numeric_limits<RealType>::epsilon();
267 #endif
268  }
269 
270  /** increment QMCCounter
271  *
272  * QMCCounter is the number of times any QMC section is processed.
273  */
274  inline void advanceQMCCounter() { iParam[B_COUNTER]++; }
275  inline void regressQMCCounter() { iParam[B_COUNTER]--; }
276 
277  /** get the EstimatorManager */
279 
280  /** set the EstimatorManager
281  * @param est estimator created by the first QMCDriver
282  * this assumes estimator managers are reused section to section
283  * */
284  void setEstimatorManager(std::unique_ptr<EstimatorManagerBase> est) { MyEstimator = std::move(est); }
285 
286  /** initialize the WalkerController
287  * @param mcwc Walkers
288  * @param fixW true, if reconfiguration with the fixed number of walkers is used
289  * @param killwalker
290  * @return number of copies to make in case targetwalkers changed
291  */
292  int initWalkerController(MCWalkerConfiguration& mcwc, bool fixW, bool killwalker);
293 
294  /** initialize reptile stats
295  *
296  *
297  */
299 
300  /** determine trial and reference energies
301  */
303 
304  /** return the bare branch weight
305  *
306  * This is equivalent to calling branchWeight(enew,eold,1.0,1.0)
307  */
308  inline RealType branchWeightBare(RealType enew, RealType eold) const
309  {
310  return std::exp(vParam[SBVP::TAUEFF] * (vParam[SBVP::ETRIAL] - 0.5 * (enew + eold)));
311  }
312 
313  /** return the bare branch weight with a filtering using an energy window
314  *
315  * Cutoff values are set by the variance
316  */
318  {
319  FullPrecRealType taueff_ = vParam[SBVP::TAUEFF] * 0.5;
320  FullPrecRealType x = std::max(vParam[SBVP::EREF] - enew, vParam[SBVP::EREF] - eold);
321  if (x > vParam[SBVP::BRANCHMAX])
322  taueff_ = 0.0;
323  else if (x > vParam[SBVP::BRANCHCUTOFF])
324  taueff_ *= (1.0 - (x - vParam[SBVP::BRANCHCUTOFF]) * vParam[SBVP::BRANCHFILTER]);
325  return std::exp(taueff_ * (vParam[SBVP::ETRIAL] * 2.0 - enew - eold));
326  }
327 
328  inline RealType symLinkAction(RealType logGf, RealType logGb, RealType enew, RealType eold) const
329  {
330  RealType driftaction = -0.5 * (logGf + logGb);
331  //RealType energyaction =
332  RealType taueff_ = vParam[SBVP::TAUEFF] * 0.5;
333  RealType x = std::max(vParam[SBVP::EREF] - enew, vParam[SBVP::EREF] - eold);
334  if (x > vParam[SBVP::BRANCHMAX])
335  taueff_ = 0.0;
336  else if (x > vParam[SBVP::BRANCHCUTOFF])
337  taueff_ *= (1.0 - (x - vParam[SBVP::BRANCHCUTOFF]) * vParam[SBVP::BRANCHFILTER]);
338  RealType energyaction = taueff_ * (enew + eold);
339  return driftaction + energyaction;
340  }
341 
342  inline RealType symLinkActionBare(RealType logGf, RealType logGb, RealType enew, RealType eold) const
343  {
344  RealType driftaction = -0.5 * (logGf + logGb);
345  RealType taueff_ = vParam[SBVP::TAUEFF] * 0.5;
346  RealType energyaction = taueff_ * (enew + eold);
347  // RealType wavefunctionaction= -psinew + psiold;
348  return driftaction + energyaction;
349  }
350 
351  inline RealType DMCLinkAction(RealType enew, RealType eold) const
352  {
353  RealType taueff_ = vParam[SBVP::TAUEFF] * 0.5;
354  RealType x = std::max(vParam[SBVP::EREF] - enew, vParam[SBVP::EREF] - eold);
355  if (x > vParam[SBVP::BRANCHMAX])
356  taueff_ = 0.0;
357  else if (x > vParam[SBVP::BRANCHCUTOFF])
358  taueff_ *= (1.0 - (x - vParam[SBVP::BRANCHCUTOFF]) * vParam[SBVP::BRANCHFILTER]);
359  return taueff_ * (enew + eold);
360  }
361  /** return the branch weight according to JCP1993 Umrigar et al. Appendix A p=1, q=0
362  * @param enew new energy
363  * @param eold old energy
364  * @param scnew \f$ V_{sc}(R_{new})/V(R_{new}) \f$
365  * @param scold \f$ V_{sc}(R_{old})/V(R_{old}) \f$
366  */
367  inline RealType branchWeight(RealType enew, RealType eold, RealType scnew, RealType scold) const
368  {
369  FullPrecRealType s1 = (vParam[SBVP::ETRIAL] - vParam[SBVP::EREF]) + (vParam[SBVP::EREF] - enew) * scnew;
370  FullPrecRealType s0 = (vParam[SBVP::ETRIAL] - vParam[SBVP::EREF]) + (vParam[SBVP::EREF] - eold) * scold;
371  return std::exp(vParam[SBVP::TAUEFF] * 0.5 * (s1 + s0));
372  }
373 
374  /** return the branch weight according to JCP1993 Umrigar et al. Appendix A
375  * @param enew new energy
376  * @param eold old energy
377  * @param scnew \f$ V_{sc}(R_{new})/V(R_{new}) \f$
378  * @param scold \f$ V_{sc}(R_{old})/V(R_{old}) \f$
379  * @param p acceptance ratio
380  */
381  inline RealType branchWeight(RealType enew, RealType eold, RealType scnew, RealType scold, RealType p) const
382  {
383  FullPrecRealType s1 = (vParam[SBVP::ETRIAL] - vParam[SBVP::EREF]) + (vParam[SBVP::EREF] - enew) * scnew;
384  FullPrecRealType s0 = (vParam[SBVP::ETRIAL] - vParam[SBVP::EREF]) + (vParam[SBVP::EREF] - eold) * scold;
385  return std::exp(vParam[SBVP::TAUEFF] * (p * 0.5 * (s1 - s0) + s0));
386  //return std::exp(TauEff*(p*0.5*(sp-sq)+sq));
387  }
388 
389  /** return the branch weight according to JCP1993 Umrigar et al. Appendix A p=1, q=0
390  * @param enew new energy
391  * @param eold old energy
392  * @param scnew \f$ V_{sc}(R_{new})/V(R_{new}) \f$
393  * @param scold \f$ V_{sc}(R_{old})/V(R_{old}) \f$
394  * @param taueff
395  */
396  inline RealType branchWeightTau(RealType enew, RealType eold, RealType scnew, RealType scold, RealType taueff)
397  {
398  ScaleSum += scnew + scold;
399  ScaleNum += 2;
400  FullPrecRealType scavg = (ScaleNum > 10000) ? ScaleSum / (RealType)ScaleNum : 1.0;
401  FullPrecRealType s1 = (vParam[SBVP::ETRIAL] - vParam[SBVP::EREF]) + (vParam[SBVP::EREF] - enew) * scnew / scavg;
402  FullPrecRealType s0 = (vParam[SBVP::ETRIAL] - vParam[SBVP::EREF]) + (vParam[SBVP::EREF] - eold) * scold / scavg;
403  return std::exp(taueff * 0.5 * (s1 + s0));
404  }
405 
406  inline RealType getEref() const { return vParam[SBVP::EREF]; }
407  inline RealType getEtrial() const { return vParam[SBVP::ETRIAL]; }
408  inline RealType getTau() const { return vParam[SBVP::TAU]; }
409  inline RealType getTauEff() const { return vParam[SBVP::TAUEFF]; }
410 
411  /** perform branching
412  * @param iter current step
413  * @param w Walker configuration
414  */
415  void branch(int iter, MCWalkerConfiguration& w);
416 
417  /** update RMC counters and running averages.
418  * @param iter the iteration
419  * @param w the walker ensemble
420  */
421  void collect(int iter, MCWalkerConfiguration& w);
422 
423  /** restart averaging
424  * @param counter Counter to determine the cummulative average will be reset.
425  */
426  void flush(int counter);
427 
428  /** reset the internal parameters */
429  void reset();
430 
431  /** reset the internal parameters
432  * @return new target population over old target population
433  *
434  * only used by legacy drivers
435  */
436  int resetRun(xmlNodePtr cur);
437 
438  bool put(xmlNodePtr cur);
439 
440  /** write the state
441  * @param fname name of the configuration file
442  * @param overwrite NOT USED
443  */
444  void write(const std::string& fname, bool overwrite = true);
445 
446  void read(const std::string& fname);
447 
448  /** create map between the parameter name and variables */
449  void registerParameters();
450 
451  ///start a run
452  void start(const std::string& froot, bool append = false);
453  ///finalize the simulation
455 
456 private:
457  ///set branch cutoff, max, filter
458  void setBranchCutoff(FullPrecRealType variance,
459  FullPrecRealType targetSigma,
460  FullPrecRealType maxSigma,
461  int Nelec = 0);
462 
463  ///disable branching for debugging
465 };
466 
467 std::ostream& operator<<(std::ostream& os, SimpleFixedNodeBranch::VParamType& rhs);
468 
469 } // namespace qmcplusplus
470 #endif
void collect(int iter, MCWalkerConfiguration &w)
update RMC counters and running averages.
HamiltonianRef::FullPrecRealType FullPrecRealType
std::bitset< B_MODE_MAX > BranchModeType
booleans to set the branch modes
accumulator_set< RealType > R2Center
a simple accumulator for reptation&#39;s center slice
A set of walkers that are to be advanced by Metropolis Monte Carlo.
helper functions for EinsplineSetBuilder
Definition: Configuration.h:43
void reset()
reset the internal parameters
void checkParameters(MCWalkerConfiguration &w)
determine trial and reference energies
controlling parameters of full precision real type
FullPrecRealType ScaleSum
Used for the average scaling.
RealType branchWeightBare(RealType enew, RealType eold) const
return the bare branch weight
std::string branching_cutoff_scheme
scheme of branching cutoff
bool phaseChanged(RealType psi0) const
accumulator_set< RealType > R2Proposed
a simple accumulator for energy
EstimatorManagerBase * getEstimatorManager()
get the EstimatorManager
void branch(int iter, MCWalkerConfiguration &w)
perform branching
RealType DMCLinkAction(RealType enew, RealType eold) const
RealType branchWeight(RealType enew, RealType eold, RealType scnew, RealType scold) const
return the branch weight according to JCP1993 Umrigar et al.
void start(const std::string &froot, bool append=false)
start a run
RealType symLinkActionBare(RealType logGf, RealType logGb, RealType enew, RealType eold) const
void advanceQMCCounter()
increment QMCCounter
xmlNodePtr myNode
save xml element
RealType symLinkAction(RealType logGf, RealType logGb, RealType enew, RealType eold) const
SimpleFixedNodeBranch(RealType tau, int nideal)
Constructor.
void write(const std::string &fname, bool overwrite=true)
write the state
accumulator_set< FullPrecRealType > EnergyHist
a simple accumulator for energy
void setBranchCutoff(FullPrecRealType variance, FullPrecRealType targetSigma, FullPrecRealType maxSigma, int Nelec=0)
set branch cutoff, max, filter
void flush(int counter)
restart averaging
ParameterSet m_param
set of parameters
FullPrecRealType & operator[](PAR_ENUM sbvp)
FullPrecRealType logN
Feed*log(N)
std::unique_ptr< WalkerControlBase > BackupWalkerController
Backup WalkerController for mixed DMC.
Manages the state of QMC sections and handles population control for DMCs.
1 to use taueff accordning to JCP 93, 0 to use tau
frequency of the trial energy updates, default 1
MakeReturn< UnaryNode< FnCos, typename CreateLeaf< Vector< T1, C1 > >::Leaf_t > >::Expression_t cos(const Vector< T1, C1 > &l)
class to handle a set of parameters
Definition: ParameterSet.h:27
RealType branchWeight(FullPrecRealType enew, FullPrecRealType eold) const
return the bare branch weight with a filtering using an energy window
int initWalkerController(MCWalkerConfiguration &mcwc, bool fixW, bool killwalker)
initialize the WalkerController
1 to kill walkers when a node crossing is detected
1 for the standard dmc, 0 for the comb method
RealType branchWeight(RealType enew, RealType eold, RealType scnew, RealType scold, RealType p) const
return the branch weight according to JCP1993 Umrigar et al.
std::ostream & operator<<(std::ostream &out, const AntiSymTensor< T, D > &rhs)
MakeReturn< UnaryNode< FnExp, typename CreateLeaf< Vector< T1, C1 > >::Leaf_t > >::Expression_t exp(const Vector< T1, C1 > &l)
Define a accumulator whose average is evaluated for a moving block of a fixed steps.
Manager class of scalar estimators.
warmup steps, valid when BranchMode[D_DMCSTAGE] == 0
void registerParameters()
create map between the parameter name and variables
void read(const std::string &fname)
Class to manage a set of ScalarEstimators.
std::vector< RealType > LogNorm
LogNorm.
RealType branchWeightTau(RealType enew, RealType eold, RealType scnew, RealType scold, RealType taueff)
return the branch weight according to JCP1993 Umrigar et al.
std::array< FullPrecRealType, static_cast< size_t >(SBVP ::VPARAM_MAX)> Base
Definition: SFNBranch.h:147
std::vector< std::string > sParam
string parameters
void initReptile(MCWalkerConfiguration &w)
initialize reptile stats
bool put(xmlNodePtr cur)
Parse the xml file for parameters.
interval between branch, see population control
QTFull::RealType FullPrecRealType
Definition: Configuration.h:66
const FullPrecRealType & operator[](PAR_ENUM sbvp) const
traits for QMC variables
Definition: Configuration.h:49
std::unique_ptr< EstimatorManagerBase > MyEstimator
std::unique_ptr< WalkerControlBase > WalkerController
WalkerController.
accumulator_set< RealType > R2Accepted
a simple accumulator for energy
void setEstimatorManager(std::unique_ptr< EstimatorManagerBase > est)
set the EstimatorManager
int resetRun(xmlNodePtr cur)
reset the internal parameters
target total number of walkers per mpi group
Declaration of a MCWalkerConfiguration.
A container class to represent a walker.
Definition: Walker.h:49
int ToDoSteps
number of remaning steps for a specific tasks
Define and declare accumulator_set.
void finalize(MCWalkerConfiguration &w)
finalize the simulation
accumulator_set< FullPrecRealType > VarianceHist
a simple accumulator for variance
std::string debug_disable_branching_
disable branching for debugging