QMCPACK
Walker.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) 2016 Jeongnim Kim and QMCPACK developers.
6 //
7 // File developed by: D. Das, University of Illinois at Urbana-Champaign
8 // Ken Esler, kpesler@gmail.com, University of Illinois at Urbana-Champaign
9 // Miguel Morales, moralessilva2@llnl.gov, Lawrence Livermore National Laboratory
10 // Jeremy McMinnis, jmcminis@gmail.com, University of Illinois at Urbana-Champaign
11 // Jeongnim Kim, jeongnim.kim@gmail.com, University of Illinois at Urbana-Champaign
12 // Raymond Clay III, j.k.rofling@gmail.com, Lawrence Livermore National Laboratory
13 // Ye Luo, yeluo@anl.gov, Argonne National Laboratory
14 // Mark A. Berrill, berrillma@ornl.gov, Oak Ridge National Laboratory
15 // Jeongnim Kim, jeongnim.kim@intel.com, Intel Corp
16 //
17 // File created by: Jeongnim Kim, jeongnim.kim@gmail.com, University of Illinois at Urbana-Champaign
18 //////////////////////////////////////////////////////////////////////////////////////
19 
20 
21 #ifndef QMCPLUSPLUS_WALKER_H
22 #define QMCPLUSPLUS_WALKER_H
23 
24 #include "OhmmsPETE/OhmmsMatrix.h"
26 #include "Pools/PooledData.h"
27 #include "Pools/PooledMemory.h"
29 
30 namespace qmcplusplus
31 {
32 /** A container class to represent a walker.
33  *
34  * A walker stores the particle configurations {R} and a property container.
35  * RealTypehe template (P)articleSet(A)ttribute is a generic container of position types.
36  * RealTypehe template (G)radient(A)ttribute is a generic container of gradients types.
37  * Data members for each walker
38  * - walker_id_ : identity for a walker. default is 0.
39  * - Age : generation after a move is accepted.
40  * - Weight : weight to take the ensemble averages
41  * - Multiplicity : multiplicity for branching. Probably can be removed.
42  * - Properties : 2D container. RealType first index corresponds to the H/Psi index and second index >=WP::NUMPROPERTIES.
43  * - DataSet : a contiguous buffer providing a state snapshot of most/all walker data.
44  Much complicated state management arises in keeping this up to date,
45  or purposefully out of sync with actual datamembers. Here and in TWF, HAMs and PARTICLE sets
46  associated with the walker.
47  */
48 template<typename t_traits, typename p_traits>
49 class Walker
50 {
51 public:
53  enum
54  {
56  };
57  /** typedef for real data type */
58  using RealType = typename t_traits::RealType;
59  /** typedef for estimator real data type */
61  /** typedef for value data type. */
62  using ValueType = typename t_traits::ValueType;
63  /** array of particles */
64  using ParticlePos = typename p_traits::ParticlePos;
65  /** array of scalars */
66  using ParticleScalar = typename p_traits::ParticleScalar;
67  /** array of gradients */
68  using ParticleGradient = typename p_traits::ParticleGradient;
69  /** array of laplacians */
70  using ParticleLaplacian = typename p_traits::ParticleLaplacian;
71  /** typedef for value data type. */
72  using SingleParticleValue = typename p_traits::SingleParticleValue;
73 
74  ///typedef for the property container, fixed size
76 
77  /** @{
78  * Not really "buffers", "walker message" also used to serialize walker, rename
79  */
82  /** }@ */
83 
84 private:
85  /** in legacy the ancients have said only:
86  * id reserved for forward walking
87  */
88  long walker_id_ = 0;
89  /** in legacy the ancients have said only:
90  * id reserved for forward walking
91  */
92  long parent_id_ = 0;
93 
94 public:
95  /** allegedly DMCgeneration
96  * PD: I can find no evidence it is ever updated anywhere in the code.
97  */
98  int Generation = 0;
99  ///Age of this walker age is incremented when a walker is not moved after a sweep
100  int Age = 0;
101  ///Weight of the walker
103  /** Number of copies for branching
104  * When Multiplicity = 0, this walker will be destroyed.
105  */
107  /// mark true if this walker is being sent.
109  /// if true, this walker is either copied or tranferred from another MPI rank.
110  bool wasTouched = true;
111 
112  /** The configuration vector (3N-dimensional vector to store
113  the positions of all the particles for a single walker)*/
115 
116  //Dynamical spin variable.
118 #if !defined(SOA_MEMORY_OPTIMIZED)
119  /** \f$ \nabla_i d\log \Psi for the i-th particle */
121  /** \f$ \nabla^2_i d\log \Psi for the i-th particle */
123 #endif
124  ///scalar properties of a walker
126 
127  /** Property history vector
128  *
129  * these are used as fixed length cyclic traces of a "property"
130  */
131  std::vector<std::vector<FullPrecRealType>> PropertyHistory;
132  std::vector<int> PHindex;
133 
134  ///buffer for the data for particle-by-particle update
137 
138  // This is very useful for debugging transfer damage to walkers
139 #ifndef NDEBUG
140 private:
141  bool has_been_on_wire_ = false;
142 
143 public:
144  bool get_has_been_on_wire() const { return has_been_on_wire_; }
145  void set_has_been_on_wire(bool tf) { has_been_on_wire_ = tf; }
146 #endif
147 
148  long getWalkerID() const { return walker_id_; }
149  long getParentID() const { return parent_id_; }
150  /** set function for walker walker_id_
151  * only necessary because as an optimization we reuse walkers.
152  */
153  void setWalkerID(long walker_id) { walker_id_ = walker_id; }
154  void setParentID(long parent_id) { parent_id_ = parent_id; }
155 
156  /// create a walker for n-particles
157  inline explicit Walker(int nptcl = 0) : Properties(1, WP::NUMPROPERTIES, 1, WP::MAXPROPERTIES)
158  {
159  if (nptcl > 0)
160  resize(nptcl);
161  }
162 
163  Walker(const Walker& a) : Properties(1, WP::NUMPROPERTIES, 1, WP::MAXPROPERTIES) { makeCopy(a); }
164  Walker(const Walker& a, long walker_id, long parent_id)
165  : walker_id_(walker_id), parent_id_(parent_id), Properties(1, WP::NUMPROPERTIES, 1, WP::MAXPROPERTIES)
166  {
167  makeCopy(a);
168  }
169 
170  /** create a valid walker for n-particles (batched version)
171  * the goal is for this walker is valid after construction
172  * without the need for more initialization functions to be called.
173  */
174  inline explicit Walker(long walker_id, long parent_id, int nptcl = 0)
175  : walker_id_(walker_id), parent_id_(parent_id), Properties(1, WP::NUMPROPERTIES, 1, WP::MAXPROPERTIES)
176  {
177  if (nptcl > 0)
178  resize(nptcl);
179  }
180 
181  inline int addPropertyHistory(int leng)
182  {
183  int newL = PropertyHistory.size();
184  PropertyHistory.push_back(std::vector<RealType>(leng, 0.0));
185  PHindex.push_back(0);
186  return newL;
187  }
188 
189  inline void deletePropertyHistory() { PropertyHistory.clear(); }
190 
191  inline void resetPropertyHistory()
192  {
193  for (int i = 0; i < PropertyHistory.size(); i++)
194  {
195  PHindex[i] = 0;
196  for (int k = 0; k < PropertyHistory[i].size(); k++)
197  {
198  PropertyHistory[i][k] = 0.0;
199  }
200  }
201  }
202 
203  inline void addPropertyHistoryPoint(int index, FullPrecRealType data)
204  {
205  PropertyHistory[index][PHindex[index]] = (data);
206  PHindex[index]++;
207  if (PHindex[index] == PropertyHistory[index].size())
208  PHindex[index] = 0;
209  // PropertyHistory[index].pop_back();
210  }
211 
212  inline FullPrecRealType getPropertyHistorySum(int index, int endN)
213  {
214  FullPrecRealType mean = 0.0;
215  typename std::vector<FullPrecRealType>::const_iterator phStart;
216  phStart = PropertyHistory[index].begin() + PHindex[index];
217  for (int i = 0; i < endN; phStart++, i++)
218  {
219  if (phStart >= PropertyHistory[index].end())
220  phStart -= PropertyHistory[index].size();
221  mean += (*phStart);
222  }
223  return mean;
224  }
225 
226  ///assignment operator
227  inline Walker& operator=(const Walker& a)
228  {
229  if (this != &a)
230  makeCopy(a);
231  return *this;
232  }
233 
234  ///return the number of particles per walker
235  inline int size() const { return R.size(); }
236 
237  ///resize for n particles
238  inline void resize(int nptcl)
239  {
240  R.resize(nptcl);
241  spins.resize(nptcl);
242  G.resize(nptcl);
243  L.resize(nptcl);
244  }
245 
246  ///copy the content of a walker
247  inline void makeCopy(const Walker& a)
248  {
252  Age = a.Age;
253  Weight = a.Weight;
255  if (R.size() != a.R.size())
256  resize(a.R.size());
257  R = a.R;
258  if (spins.size() != a.spins.size())
259  resize(a.spins.size());
260  spins = a.spins;
261 #if !defined(SOA_MEMORY_OPTIMIZED)
262  G = a.G;
263  L = a.L;
264 #endif
266  DataSet = a.DataSet;
267  block_end = a.block_end;
269  if (PropertyHistory.size() != a.PropertyHistory.size())
270  PropertyHistory.resize(a.PropertyHistory.size());
271  for (int i = 0; i < PropertyHistory.size(); i++)
273  PHindex = a.PHindex;
274  }
275 
276  //return the address of the values of Hamiltonian terms
278 
279  //return the address of the values of Hamiltonian terms
280  inline const FullPrecRealType* getPropertyBase() const { return Properties.data(); }
281 
282  ///return the address of the i-th properties
283  inline FullPrecRealType* getPropertyBase(int i) { return Properties[i]; }
284 
285  ///return the address of the i-th properties
286  inline const FullPrecRealType* getPropertyBase(int i) const { return Properties[i]; }
287 
288  /** reset the property of a walker
289  *@param logpsi \f$\log |\Psi|\f$
290  *@param sigN sign of the trial wavefunction
291  *@param ene the local energy
292  *
293  *Assign the values and reset the age
294  * but leave the weight and multiplicity
295  */
297  {
298  Age = 0;
299  //Weight=1.0;
300  Properties(WP::LOGPSI) = logpsi;
301  Properties(WP::SIGN) = sigN;
302  Properties(WP::LOCALENERGY) = ene;
303  }
304 
305  /** reset the property of a walker
306  * @param logpsi \f$\log |\Psi|\f$
307  * @param sigN sign of the trial wavefunction
308  * @param ene the local energy
309  * @param r2a \f$r^2\f$ for the accepted moves
310  * @param r2p \f$r^2\f$ for the proposed moves
311  * @param vq \f$\bar{V}/V\f$ scaling to control node divergency in JCP 93
312  *
313  *Assign the values and reset the age
314  * but leave the weight and multiplicity
315  */
316  inline void resetProperty(FullPrecRealType logpsi,
317  FullPrecRealType sigN,
318  FullPrecRealType ene,
319  FullPrecRealType r2a,
320  FullPrecRealType r2p,
321  FullPrecRealType vq)
322  {
323  Age = 0;
324  Properties(WP::LOGPSI) = logpsi;
325  Properties(WP::SIGN) = sigN;
326  Properties(WP::LOCALENERGY) = ene;
327  Properties(WP::R2ACCEPTED) = r2a;
328  Properties(WP::R2PROPOSED) = r2p;
329  Properties(WP::DRIFTSCALE) = vq;
330  }
331 
332  /** marked to die
333  *
334  * Multiplicity and weight are set to zero.
335  */
336  inline void willDie()
337  {
338  Multiplicity = 0;
339  Weight = 0.0;
340  }
341 
342  /** reset the walker weight, multiplicity and age */
343  inline void reset()
344  {
345  Age = 0;
346  Multiplicity = 1.0e0;
347  Weight = 1.0e0;
348  }
349 
350  inline void resizeProperty(int n, int m) { Properties.resize(n, m); }
351 
352 
353  /** byte size for a packed message
354  *
355  * walker_id_, Age, Properties, R, Drift, DataSet is packed
356  */
357  inline size_t byteSize()
358  {
359  // TODO: fix this! this is a non intuitive side effect for a size call
360  // breaks a bunch of things that could be const
361  if (!DataSet.size())
362  {
363  registerData();
364  DataSet.allocate();
365  }
366  return DataSet.byteSize();
367  }
368 
370  {
371  // walker data must be placed at the beginning
372  assert(DataSet.size() == 0);
373  // scalars
377  DataSet.add(Age);
378  // vectors
379  assert(R.size() != 0);
380  DataSet.add(R.first_address(), R.last_address());
381  assert(spins.size() != 0);
382  DataSet.add(spins.first_address(), spins.last_address());
383 #if !defined(SOA_MEMORY_OPTIMIZED)
384  assert(G.size() != 0);
385  DataSet.add(G.first_address(), G.last_address());
386  assert(L.size() != 0);
387  DataSet.add(L.first_address(), L.last_address());
388 #endif
389  //Don't add the nLocal but the actual allocated size. We want to register once for the life of a
390  //walker so we leave space for additional properties.
392  //DataSet.add(Properties.first_address(), Properties.last_address());
393 
394  // \todo likely to be broken if the Properties change above is needed.
395  for (int iat = 0; iat < PropertyHistory.size(); iat++)
396  DataSet.add(PropertyHistory[iat].data(), PropertyHistory[iat].data() + PropertyHistory[iat].size());
397  DataSet.add(PHindex.data(), PHindex.data() + PHindex.size());
400  }
401 
403  {
404  assert(DataSet.size() != 0);
405  DataSet.rewind();
407  // vectors
408  assert(R.size() != 0);
409  DataSet.get(R.first_address(), R.last_address());
410  assert(spins.size() != 0);
411  DataSet.get(spins.first_address(), spins.last_address());
412 #if !defined(SOA_MEMORY_OPTIMIZED)
413  assert(G.size() != 0);
414  DataSet.get(G.first_address(), G.last_address());
415  assert(L.size() != 0);
416  DataSet.get(L.first_address(), L.last_address());
417 #endif
419  for (int iat = 0; iat < PropertyHistory.size(); iat++)
420  DataSet.get(PropertyHistory[iat].data(), PropertyHistory[iat].data() + PropertyHistory[iat].size());
421  DataSet.get(PHindex.data(), PHindex.data() + PHindex.size());
422  assert(block_end == DataSet.current());
423  assert(scalar_end == DataSet.current_scalar());
424  }
425 
426  // In Clang 4.0.1 it is unclear why but attibute list cannot go at the end
427  // when a template declaration follows
429  {
430  DataSet.rewind();
432  // vectors
433  DataSet.put(R.first_address(), R.last_address());
434  DataSet.put(spins.first_address(), spins.last_address());
435 #if !defined(SOA_MEMORY_OPTIMIZED)
436  DataSet.put(G.first_address(), G.last_address());
437  DataSet.put(L.first_address(), L.last_address());
438 #endif
440  for (int iat = 0; iat < PropertyHistory.size(); iat++)
441  DataSet.put(PropertyHistory[iat].data(), PropertyHistory[iat].data() + PropertyHistory[iat].size());
442  DataSet.put(PHindex.data(), PHindex.data() + PHindex.size());
443  assert(block_end == DataSet.current());
444  assert(scalar_end == DataSet.current_scalar());
445  }
446 
447  template<class Msg>
448  inline Msg& putMessage(Msg& m)
449  {
450  // Pack DataSet buffer
451  if (!DataSet.size())
452  {
453  registerData();
454  DataSet.allocate();
455  }
456  updateBuffer();
457  m.Pack(DataSet.data(), DataSet.size());
458  return m;
459  }
460 
461  template<class Msg>
462  inline Msg& getMessage(Msg& m)
463  {
464  if (!DataSet.size())
465  {
466  registerData();
467  DataSet.allocate();
468  }
469  m.Unpack(DataSet.data(), DataSet.size());
470  copyFromBuffer();
471  return m;
472  }
473 };
474 
475 template<class RealType, class PA>
476 std::ostream& operator<<(std::ostream& out, const Walker<RealType, PA>& rhs)
477 {
478  copy(rhs.Properties.begin(), rhs.Properties.end(), std::ostream_iterator<double>(out, " "));
479  out << std::endl;
480  out << rhs.R;
481  return out;
482 }
483 } // namespace qmcplusplus
484 
485 #endif
const FullPrecRealType * getPropertyBase() const
Definition: Walker.h:280
std::vector< int > PHindex
Definition: Walker.h:132
Walker(int nptcl=0)
create a walker for n-particles
Definition: Walker.h:157
int size() const
return the number of particles per walker
Definition: Walker.h:235
HamiltonianRef::FullPrecRealType FullPrecRealType
FullPrecRealType * getPropertyBase(int i)
return the address of the i-th properties
Definition: Walker.h:283
PropertyContainer_t Properties
scalar properties of a walker
Definition: Walker.h:125
typename qmcplusplus::PtclOnLatticeTraits ::ParticleGradient ParticleGradient
array of gradients
Definition: Walker.h:68
WFBuffer_t DataSet
buffer for the data for particle-by-particle update
Definition: Walker.h:135
typename qmcplusplus::PtclOnLatticeTraits ::ParticleScalar ParticleScalar
array of scalars
Definition: Walker.h:66
helper functions for EinsplineSetBuilder
Definition: Configuration.h:43
std::vector< std::vector< FullPrecRealType > > PropertyHistory
Property history vector.
Definition: Walker.h:131
void copyFromBuffer()
Definition: Walker.h:402
void copy(const RHS &rhs)
Methods for assignment or copy of identically sized or smaller ConstantSizeMatrix<T, ALLOC>.
typename qmcplusplus::PtclOnLatticeTraits ::ParticlePos ParticlePos
array of particles
Definition: Walker.h:64
void updateBuffer()
Definition: Walker.h:428
void registerData()
Definition: Walker.h:369
void willDie()
marked to die
Definition: Walker.h:336
size_t byteSize()
byte size for a packed message
Definition: Walker.h:357
long parent_id_
in legacy the ancients have said only: id reserved for forward walking
Definition: Walker.h:92
void allocate()
allocate the data
Definition: PooledMemory.h:104
bool SendInProgress
mark true if this walker is being sent.
Definition: Walker.h:108
void resetProperty(FullPrecRealType logpsi, FullPrecRealType sigN, FullPrecRealType ene, FullPrecRealType r2a, FullPrecRealType r2p, FullPrecRealType vq)
reset the property of a walker
Definition: Walker.h:316
int Generation
allegedly DMCgeneration PD: I can find no evidence it is ever updated anywhere in the code...
Definition: Walker.h:98
typename qmcplusplus::QMCTraits ::FullPrecRealType FullPrecRealType
typedef for estimator real data type
Definition: Walker.h:60
int Age
Age of this walker age is incremented when a walker is not moved after a sweep.
Definition: Walker.h:100
void set_has_been_on_wire(bool tf)
Definition: Walker.h:145
bool wasTouched
if true, this walker is either copied or tranferred from another MPI rank.
Definition: Walker.h:110
size_t block_end
Definition: Walker.h:136
void copy(const Array< T1, 3 > &src, Array< T2, 3 > &dest)
Definition: Blitz.h:639
void makeCopy(const Walker &a)
copy the content of a walker
Definition: Walker.h:247
ParticleScalar spins
Definition: Walker.h:117
typename qmcplusplus::QMCTraits ::ValueType ValueType
typedef for value data type.
Definition: Walker.h:62
long getParentID() const
Definition: Walker.h:149
void resetPropertyHistory()
Definition: Walker.h:191
void resize(int nptcl)
resize for n particles
Definition: Walker.h:238
T * data()
return the address of the first element
Definition: PooledMemory.h:187
Walker(long walker_id, long parent_id, int nptcl=0)
create a valid walker for n-particles (batched version) the goal is for this walker is valid after co...
Definition: Walker.h:174
size_type byteSize() const
return the size of the data
Definition: PooledMemory.h:70
void setParentID(long parent_id)
Definition: Walker.h:154
void deletePropertyHistory()
Definition: Walker.h:189
int addPropertyHistory(int leng)
Definition: Walker.h:181
bool has_been_on_wire_
Definition: Walker.h:141
Walker & operator=(const Walker &a)
assignment operator
Definition: Walker.h:227
typename qmcplusplus::PtclOnLatticeTraits ::ParticleLaplacian ParticleLaplacian
array of laplacians
Definition: Walker.h:70
void reset()
reset the walker weight, multiplicity and age
Definition: Walker.h:343
size_t scalar_end
Definition: Walker.h:136
Msg & putMessage(Msg &m)
Definition: Walker.h:448
size_type current() const
Definition: PooledMemory.h:76
QMCTraits::RealType RealType
long getWalkerID() const
Definition: Walker.h:148
Msg & getMessage(Msg &m)
Definition: Walker.h:462
size_type size() const
return the size of the data
Definition: PooledMemory.h:73
typename qmcplusplus::QMCTraits ::RealType RealType
typedef for real data type
Definition: Walker.h:58
Indexes
an enum denoting index of physical properties
typename qmcplusplus::PtclOnLatticeTraits ::SingleParticleValue SingleParticleValue
typedef for value data type.
Definition: Walker.h:72
FullPrecRealType getPropertyHistorySum(int index, int endN)
Definition: Walker.h:212
FullPrecRealType Weight
Weight of the walker.
Definition: Walker.h:102
LatticeGaussianProduct::ValueType ValueType
void setWalkerID(long walker_id)
set function for walker walker_id_ only necessary because as an optimization we reuse walkers...
Definition: Walker.h:153
const FullPrecRealType * getPropertyBase(int i) const
return the address of the i-th properties
Definition: Walker.h:286
bool get_has_been_on_wire() const
Definition: Walker.h:144
FullPrecRealType * getPropertyBase()
Definition: Walker.h:277
size_type current_scalar() const
Definition: PooledMemory.h:79
FullPrecRealType Multiplicity
Number of copies for branching When Multiplicity = 0, this walker will be destroyed.
Definition: Walker.h:106
ACC::value_type mean(const ACC &ac)
Definition: accumulators.h:147
void rewind(size_type cur=0, size_type cur_scalar=0)
set the cursors
Definition: PooledMemory.h:85
void addPropertyHistoryPoint(int index, FullPrecRealType data)
Definition: Walker.h:203
A container class to represent a walker.
Definition: Walker.h:49
void put(std::complex< T1 > &x)
Definition: PooledMemory.h:165
Define a serialized buffer to store anonymous data.
Walker(const Walker &a)
Definition: Walker.h:163
void resetProperty(FullPrecRealType logpsi, FullPrecRealType sigN, FullPrecRealType ene)
reset the property of a walker
Definition: Walker.h:296
Walker(const Walker &a, long walker_id, long parent_id)
Definition: Walker.h:164
ParticleLaplacian L
^2_i d for the i-th particle
Definition: Walker.h:122
void resizeProperty(int n, int m)
Definition: Walker.h:350
ParticlePos R
The configuration vector (3N-dimensional vector to store the positions of all the particles for a sin...
Definition: Walker.h:114
void add(std::complex< T1 > &x)
Definition: PooledMemory.h:113
long walker_id_
}@
Definition: Walker.h:88
void get(std::complex< T1 > &x)
Definition: PooledMemory.h:132