QMCPACK
CrystalLattice.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: Ken Esler, kpesler@gmail.com, University of Illinois at Urbana-Champaign
8 // Jeremy McMinnis, jmcminis@gmail.com, University of Illinois at Urbana-Champaign
9 // Jeongnim Kim, jeongnim.kim@gmail.com, University of Illinois at Urbana-Champaign
10 // Jaron T. Krogel, krogeljt@ornl.gov, Oak Ridge National Laboratory
11 // Raymond Clay III, j.k.rofling@gmail.com, Lawrence Livermore National Laboratory
12 // Ye Luo, yeluo@anl.gov, Argonne National Laboratory
13 // Mark A. Berrill, berrillma@ornl.gov, Oak Ridge National Laboratory
14 //
15 // File created by: Jeongnim Kim, jeongnim.kim@gmail.com, University of Illinois at Urbana-Champaign
16 //////////////////////////////////////////////////////////////////////////////////////
17 
18 
19 /**@file CrystalLattice.h
20  *@brief Declaration of CrystalLattice<T,D>
21  */
22 #ifndef OHMMS_CRYSTALLATTICE_H
23 #define OHMMS_CRYSTALLATTICE_H
24 #include <limits>
25 #include <iostream>
26 #include "config/stdlib/Constants.h"
27 #include "OhmmsPETE/TinyVector.h"
28 #include "OhmmsPETE/Tensor.h"
29 #include "LRBreakupParameters.h"
30 
31 namespace qmcplusplus
32 {
33 /** enumeration to classify a CrystalLattice
34  *
35  * Use std::bitset<3> for all the dimension
36  */
37 enum
38 {
39  SUPERCELL_OPEN = 0, /*!< nnn */
40  SUPERCELL_WIRE = 1, /*!< nnp */
41  SUPERCELL_SLAB = 3, /*!< npp */
42  SUPERCELL_BULK = 7, /*!< ppp */
43  SOA_OFFSET = 32 /*!< const to differentiate AoS and SoA */
44 };
45 
46 /** a class that defines a supercell in D-dimensional Euclean space.
47  *
48  *CrystalLattice handles the physical properties of a supercell, such
49  *as lattice vectors, reciprocal vectors and metric tensors and provides
50  *interfaces to access the lattice properties and convert units of
51  *position vectors or a single-particle position from Cartesian to
52  *Lattice Unit vice versa.
53  */
54 template<class T, unsigned D>
55 struct CrystalLattice : public LRBreakupParameters<T, D>
56 {
57  /// alias to the base class
59 
60  ///enumeration for the dimension of the lattice
61  enum
62  {
63  DIM = D
64  };
65  //@{
66  ///the type of scalar
67  using Scalar_t = T;
68  ///the type of a D-dimensional position vector
70  ///the type of a D-dimensional index vector
72  ///the type of a D-dimensional Tensor
74  //@}
75 
76  ///true, if off-diagonal elements are zero so that other classes can take advantage of this
78  ///supercell enumeration
80  ///The boundary condition in each direction.
82  ///The scale factor for adding vacuum.
84  //@{
85  /**@brief Physical properties of a supercell*/
86  /// Volume of a supercell
88  /// Wigner-Seitz cell radius
90  /// simulation cell radii
92  /// SimulationCellRadius*SimulationCellRadius
94  /// Wigner-Seitz cell radius in reciprocal space
96  ///Real-space unit vectors. R(i,j) i=vector and j=x,y,z
98  ///Reciprocal unit vectors. G(j,i) i=vector and j=x,y,z
100  ///Transpose of reciprocal unit vectors:
102  ///Metric tensor
104  ///Metric tensor for G vectors
106  ///Length[idim] length of the idim-th lattice vector
108  ///OneOverLength[idim] 1/length of the idim-th lattice vector
110  ///Center of the cell sum(Rv[i])/2
112  /**@brief Real-space unit vectors.
113  *
114  *Introduced to efficiently return one vector at a time.
115  *Rv[i] is D-dim vector of the ith direction.
116  */
118  /**@brief Reciprocal unit vectors.
119  *
120  *Introduced to efficiently return one vector at a time.
121  *Gv[i] is D-dim vector of the ith direction.
122  */
124  //@}
125  //angles between the two lattice vectors
127  ///true, the lattice is defined by the input instead of an artificial default
129 
130  ///default constructor, assign a huge supercell
131  CrystalLattice();
132 
133  /**@param i the index of the directional vector, \f$i\in [0,D)\f$
134  *@return The lattice vector of the ith direction
135  *@brief Provide interfaces familiar to fotran users
136  */
137  inline SingleParticlePos a(int i) const { return Rv[i]; }
138 
139  /**@param i the index of the directional vector, \f$i\in [0,D)\f$
140  *@return The reciprocal vector of the ith direction
141  *@brief Provide interfaces familiar to fotran users
142  */
143  inline SingleParticlePos b(int i) const { return Gv[i]; }
144 
145  /** Convert a cartesian vector to a unit vector.
146  * Boundary conditions are not applied.
147  */
148  template<class T1>
150  {
151  return dot(r, G);
152  }
153 
154  template<class T1>
156  {
157  SingleParticlePos val_dot;
158  val_dot = toUnit(r);
159  for (int i = 0; i < D; i++)
160  if (-std::numeric_limits<T1>::epsilon() < val_dot[i] && val_dot[i] < 0)
161  val_dot[i] = T1(0.0);
162  else
163  val_dot[i] -= std::floor(val_dot[i]);
164  return val_dot;
165  }
166 
167  /** Convert a unit vector to a cartesian vector.
168  * Boundary conditions are not applied.
169  */
170  template<class T1>
172  {
173  return dot(c, R);
174  }
175 
176  /// return true if all the open direction of reduced coordinates u are in the range [0,1)
177  inline bool isValid(const TinyVector<T, D>& u) const
178  {
179  bool inside = true;
180  for (int dim = 0; dim < D; dim++)
181  inside &= (BoxBConds[dim] || (u[dim] >= T(0) && u[dim] < T(1)));
182  return inside;
183  }
184 
185  /// return true if any direction of reduced coordinates u goes larger than 0.5
186  inline bool outOfBound(const TinyVector<T, D>& u) const
187  {
188  for (int i = 0; i < D; ++i)
189  if (std::abs(u[i]) > 0.5)
190  return true;
191  return false;
192  }
193 
194  inline void applyMinimumImage(TinyVector<T, D>& c) const
195  {
196  if (SuperCellEnum)
197  {
198  TinyVector<T, D> u = dot(c, G);
199  for (int i = 0; i < D; ++i)
200  u[i] = u[i] - round(u[i]);
201  c = dot(u, R);
202  }
203  }
204 
205  /** evaluate the cartesian distance
206  *@param ra a vector in the supercell unit
207  *@param rb a vector in the supercell unit
208  *@return Cartesian distance with two vectors in SC unit
209  *
210  @note The distance between two cartesian vectors are handled
211  *by dot function defined in OhmmsPETE/TinyVector.h
212  */
213  inline T Dot(const SingleParticlePos& ra, const SingleParticlePos& rb) const { return dot(ra, dot(M, rb)); }
214 
215  /** conversion of a reciprocal-vector
216  *@param kin an input reciprocal vector in the Reciprocal-vector unit
217  *@return k(reciprocal vector) in cartesian unit
218  */
219  inline SingleParticlePos k_cart(const SingleParticlePos& kin) const { return TWOPI * dot(G, kin); }
220 
221  /** conversion of a caresian reciprocal-vector to unit k-vector
222  *@param kin an input reciprocal vector in cartesian form
223  *@return k(reciprocal vector) as unit vector
224  */
225  inline SingleParticlePos k_unit(const SingleParticlePos& kin) const { return dot(R, kin) / TWOPI; }
226 
227  /** evaluate \f$k^2\f$
228  *
229  *@param kin an input reciprocal vector in reciprocal-vector unit
230  *@return \f$k_{in}^2\f$
231  */
232  inline T ksq(const SingleParticlePos& kin) const { return dot(kin, dot(Mg, kin)); }
233 
234  ///assignment operator
235  template<typename T1>
237  {
238  Base::LR_dim_cutoff = rhs.LR_dim_cutoff;
239  Base::LR_kc = rhs.LR_kc;
240  Base::LR_rc = rhs.LR_rc;
241  Base::num_ewald_grid_points = rhs.num_ewald_grid_points;
242  Base::ndim = rhs.ndim;
243 
245  BoxBConds = rhs.BoxBConds;
246  VacuumScale = rhs.VacuumScale;
247  R = rhs.R;
248  reset();
249  return *this;
250  }
251 
252  /** scale the lattice vectors by sc. All the internal data are reset.
253  *@param sc the scaling value
254  *@return a new CrystalLattice
255  */
257 
258  /** set the lattice vector from the command-line options
259  *@param lat a tensor representing a supercell
260  */
261  template<class TT>
262  void set(const Tensor<TT, D>& lat);
263 
264  /** Evaluate the reciprocal vectors, volume and metric tensor
265  */
266  void reset();
267 
268  // //@{
269  // /* Copy functions with unit conversion*/
270  // template<class PA> void convert(const PA& pin, PA& pout) const;
271  // template<class PA> void convert2Unit(const PA& pin, PA& pout) const;
272  // template<class PA> void convert2Cart(const PA& pin, PA& pout) const;
273  // template<class PA> void convert2Unit(PA& pout) const;
274  // template<class PA> void convert2Cart(PA& pout) const;
275  // //@}
276  //
277  // template<class PA> void applyBC(const PA& pin, PA& pout) const;
278  // template<class PA> void applyBC(PA& pos) const;
279  // template<class PA> void applyBC(const PA& pin, PA& pout, int first, int last) const;
280 
281  //! Print out CrystalLattice Data
282  void print(std::ostream&, int level = 2) const;
283 };
284 
285 } // namespace qmcplusplus
286 //including the definitions of the member functions
287 #include "CrystalLattice.cpp"
288 
289 #endif
a class that defines a supercell in D-dimensional Euclean space.
bool isValid(const TinyVector< T, D > &u) const
return true if all the open direction of reduced coordinates u are in the range [0,1)
int SuperCellEnum
supercell enumeration
SingleParticlePos Center
Center of the cell sum(Rv[i])/2.
Member function definitions of CrystalLattice<T,D>, included by CrystalLattice.h. ...
void reset()
Evaluate the reciprocal vectors, volume and metric tensor.
helper functions for EinsplineSetBuilder
Definition: Configuration.h:43
CrystalLattice< T, D > & operator=(const CrystalLattice< T1, D > &rhs)
assignment operator
Scalar_t WignerSeitzRadius_G
Wigner-Seitz cell radius in reciprocal space.
MakeReturn< UnaryNode< FnFabs, typename CreateLeaf< Vector< T1, C1 > >::Leaf_t > >::Expression_t abs(const Vector< T1, C1 > &l)
T VacuumScale
The scale factor for adding vacuum.
CrystalLattice< T, D > & operator*=(T sc)
scale the lattice vectors by sc.
Tensor_t G
Reciprocal unit vectors. G(j,i) i=vector and j=x,y,z.
void print(std::ostream &, int level=2) const
Print out CrystalLattice Data.
Tensor_t M
Metric tensor.
TinyVector< SingleParticlePos, D > Rv
Real-space unit vectors.
T ksq(const SingleParticlePos &kin) const
evaluate
SingleParticlePos Length
Length[idim] length of the idim-th lattice vector.
SingleParticlePos k_cart(const SingleParticlePos &kin) const
conversion of a reciprocal-vector
Tensor_t Gt
Transpose of reciprocal unit vectors:
Scalar_t Volume
Physical properties of a supercell.
TinyVector< int, D > BoxBConds
The boundary condition in each direction.
SingleParticlePos toUnit_floor(const TinyVector< T1, D > &r) const
SingleParticlePos OneOverLength
OneOverLength[idim] 1/length of the idim-th lattice vector.
SingleParticlePos a(int i) const
Provide interfaces familiar to fotran users.
SingleParticlePos k_unit(const SingleParticlePos &kin) const
conversion of a caresian reciprocal-vector to unit k-vector
SingleParticlePos toUnit(const TinyVector< T1, D > &r) const
Convert a cartesian vector to a unit vector.
CrystalLattice()
default constructor, assign a huge supercell
T Dot(const SingleParticlePos &ra, const SingleParticlePos &rb) const
evaluate the cartesian distance
TinyVector< SingleParticlePos, D > Gv
Reciprocal unit vectors.
Tensor< typename BinaryReturn< T1, T2, OpMultiply >::Type_t, D > dot(const AntiSymTensor< T1, D > &lhs, const AntiSymTensor< T2, D > &rhs)
bool outOfBound(const TinyVector< T, D > &u) const
return true if any direction of reduced coordinates u goes larger than 0.5
SingleParticlePos toCart(const TinyVector< T1, D > &c) const
Convert a unit vector to a cartesian vector.
Scalar_t SimulationCellRadius
simulation cell radii
bool explicitly_defined
true, the lattice is defined by the input instead of an artificial default
bool DiagonalOnly
true, if off-diagonal elements are zero so that other classes can take advantage of this ...
Scalar_t WignerSeitzRadius
Wigner-Seitz cell radius.
void applyMinimumImage(TinyVector< T, D > &c) const
Scalar_t CellRadiusSq
SimulationCellRadius*SimulationCellRadius.
Tensor_t Mg
Metric tensor for G vectors.
SingleParticlePos b(int i) const
Provide interfaces familiar to fotran users.
Tensor_t R
Real-space unit vectors. R(i,j) i=vector and j=x,y,z.
MakeReturn< UnaryNode< FnFloor, typename CreateLeaf< Vector< T1, C1 > >::Leaf_t > >::Expression_t floor(const Vector< T1, C1 > &l)