CheMPS2
ThreeDM.h
1 /*
2  CheMPS2: a spin-adapted implementation of DMRG for ab initio quantum chemistry
3  Copyright (C) 2013-2016 Sebastian Wouters
4 
5  This program is free software; you can redistribute it and/or modify
6  it under the terms of the GNU General Public License as published by
7  the Free Software Foundation; either version 2 of the License, or
8  (at your option) any later version.
9 
10  This program is distributed in the hope that it will be useful,
11  but WITHOUT ANY WARRANTY; without even the implied warranty of
12  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13  GNU General Public License for more details.
14 
15  You should have received a copy of the GNU General Public License along
16  with this program; if not, write to the Free Software Foundation, Inc.,
17  51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
18 */
19 
20 #ifndef THREEDM_CHEMPS2_H
21 #define THREEDM_CHEMPS2_H
22 
23 #include "TensorT.h"
24 #include "TensorL.h"
25 #include "TensorF0.h"
26 #include "TensorF1.h"
27 #include "TensorS0.h"
28 #include "TensorS1.h"
29 #include "Tensor3RDM.h"
30 #include "SyBookkeeper.h"
31 
32 namespace CheMPS2{
41  class ThreeDM{
42 
43  public:
44 
46 
49  ThreeDM( const SyBookkeeper * book_in, const Problem * prob_in , const bool disk_in );
50 
52  virtual ~ThreeDM();
53 
55 
62  double get_ham_index( const int cnt1, const int cnt2, const int cnt3, const int cnt4, const int cnt5, const int cnt6 ) const;
63 
65 
70  void fill_ham_index( const double alpha, const bool add, double * storage, const int last_orb_start, const int last_orb_num );
71 
73 
91  void fill_site( TensorT * denT, TensorL *** Ltens, TensorF0 **** F0tens, TensorF1 **** F1tens, TensorS0 **** S0tens, TensorS1 **** S1tens,
92  Tensor3RDM **** dm3_a_J0_doublet, Tensor3RDM **** dm3_a_J1_doublet, Tensor3RDM **** dm3_a_J1_quartet,
93  Tensor3RDM **** dm3_b_J0_doublet, Tensor3RDM **** dm3_b_J1_doublet, Tensor3RDM **** dm3_b_J1_quartet,
94  Tensor3RDM **** dm3_c_J0_doublet, Tensor3RDM **** dm3_c_J1_doublet, Tensor3RDM **** dm3_c_J1_quartet,
95  Tensor3RDM **** dm3_d_J0_doublet, Tensor3RDM **** dm3_d_J1_doublet, Tensor3RDM **** dm3_d_J1_quartet );
96 
99 
101 
102  double trace();
103 
105  void mpi_allreduce();
106 
108 
109  void save_HAM( const string filename ) const;
110 
112 
116  static void save_HAM_generic( const string filename, const int LAS, const string tag, double * array );
117 
118  private:
119 
120  //The BK containing all the irrep information
121  const SyBookkeeper * book;
122 
123  //The problem containing orbital reshuffling and symmetry information
124  const Problem * prob;
125 
126  //Whether or not to keep the full 3-RDM in memory
127  bool disk;
128 
129  //The DMRG chain length
130  int L;
131 
132  //The array length of elements and (when allocated) temp_disk_vals and temp_disk_orbs = ( disk ) ? L*L*L*L*L : L*L*L*L*L*L
133  int array_size;
134 
135  //The 3-RDM elements are stored in the HAMILTONIAN indices
136  double * elements;
137 
138  //The temporary orbitals when disk == true
139  int * temp_disk_orbs;
140 
141  //The temporary values when disk == true
142  double * temp_disk_vals;
143 
144  //The number of temporary values / orbitals
145  int temp_disk_counter;
146 
147  //Create file
148  void create_file() const;
149 
150  //Write a portion of the 3-RDM to disk
151  void write_file( const int last_ham_orb ) const;
152 
153  //Read a portion of the 3-RDM from disk
154  void read_file( const int last_ham_orb );
155 
156  //Flush the values stored in temp_disk_orbs and temp_disk_vals to disk
157  void flush_disk();
158 
159  //Set all twelve-fold permutation symmetric 3-RDM elements, using the DMRG indices.
160  void set_dmrg_index(const int cnt1, const int cnt2, const int cnt3, const int cnt4, const int cnt5, const int cnt6, const double value);
161 
162  //Partitioning 2-4-0
163  double diagram1(TensorT * denT, TensorF0 * denF0, double * workmem) const;
164 
165  //Partitioning 0-4-2
166  double diagram3(TensorT * denT, TensorF0 * denF0, double * workmem) const;
167 
168  //Partitioning 3-3-0
169  double diagram4_5_6_7_8_9(TensorT * denT, Tensor3RDM * d3tens, double * workmem, const char type) const;
170 
171  //Partitioning 2-3-1
172  double diagram10(TensorT * denT, TensorS0 * denS0, TensorL * denL, double * workmem, double * workmem2) const;
173  double diagram11(TensorT * denT, TensorS1 * denS1, TensorL * denL, double * workmem, double * workmem2) const;
174  double diagram12(TensorT * denT, TensorF0 * denF0, TensorL * denL, double * workmem, double * workmem2) const;
175  double diagram13(TensorT * denT, TensorF1 * denF1, TensorL * denL, double * workmem, double * workmem2) const;
176  double diagram14(TensorT * denT, TensorF0 * denF0, TensorL * denL, double * workmem, double * workmem2) const;
177  double diagram15(TensorT * denT, TensorF1 * denF1, TensorL * denL, double * workmem, double * workmem2) const;
178 
179  //Partitioning 1-3-2
180  double diagram16(TensorT * denT, TensorL * denL, TensorS0 * denS0, double * workmem, double * workmem2) const;
181  double diagram17(TensorT * denT, TensorL * denL, TensorS1 * denS1, double * workmem, double * workmem2) const;
182  double diagram18(TensorT * denT, TensorL * denL, TensorF0 * denF0, double * workmem, double * workmem2) const;
183  double diagram19(TensorT * denT, TensorL * denL, TensorF1 * denF1, double * workmem, double * workmem2) const;
184  double diagram20(TensorT * denT, TensorL * denL, TensorF0 * denF0, double * workmem, double * workmem2) const;
185  double diagram21(TensorT * denT, TensorL * denL, TensorF1 * denF1, double * workmem, double * workmem2) const;
186 
187  //Partitioning 2-2-2
188  void fill_tens_29_33(TensorT * denT, TensorF0 * tofill, TensorF0 * denF0, double * workmem) const;
189  void fill_tens_30_32(TensorT * denT, TensorF1 * tofill, TensorF1 * denF1, double * workmem) const;
190  void fill_tens_36_42(TensorT * denT, TensorF1 * tofill, TensorF0 * denF0, double * workmem) const;
191  void fill_tens_34_35_37_38(TensorT * denT, TensorF1 * fill34, TensorF0 * fill35, TensorF1 * fill37, TensorF1 * fill38, TensorF1 * denF1, double * workmem, double * workmem2) const;
192  void fill_tens_49_51(TensorT * denT, TensorF0 * tofill, TensorS0 * denS0, double * workmem) const;
193  void fill_tens_50_52(TensorT * denT, TensorF1 * tofill, TensorS1 * denS1, double * workmem) const;
194  void fill_tens_22_24(TensorT * denT, TensorS0 * tofill, TensorS0 * denS0, double * workmem) const;
195  void fill_tens_28(TensorT * denT, TensorS1 * tofill, TensorS0 * denS0, double * workmem) const;
196  void fill_tens_23(TensorT * denT, TensorS1 * tofill, TensorS1 * denS1, double * workmem) const;
197  void fill_tens_25_26_27(TensorT * denT, TensorS1 * fill25, TensorS1 * fill26, TensorS0 * fill27, TensorS1 * denS1, double * workmem, double * workmem2) const;
198  void fill_tens_45_47(TensorT * denT, TensorS0 * tofill, TensorF0 * denF0, double * workmem, const bool first) const;
199  void fill_tens_46_48(TensorT * denT, TensorS1 * tofill, TensorF1 * denF1, double * workmem, const bool first) const;
200 
201  //Partitioning 3-2-1 and 1-4-1
202  void fill_53_54(TensorT * denT, Tensor3RDM * tofill, TensorL * denL, double * workmem) const;
203  void fill_55_to_60(TensorT * denT, Tensor3RDM * tofill, TensorL * denL, double * workmem) const;
204  void fill_61(TensorT * denT, Tensor3RDM * tofill, TensorL * denL, double * workmem) const;
205  void fill_63_65(TensorT * denT, Tensor3RDM * fill63, Tensor3RDM * fill65, Tensor3RDM * fill67, Tensor3RDM * fill68,
206  Tensor3RDM * fill76, Tensor3RDM * fill77, TensorL * denL, double * workmem, double * workmem2) const;
207  void fill_69_78_79(TensorT * denT, Tensor3RDM * fill69, Tensor3RDM * fill78, Tensor3RDM * fill79, TensorL * denL, double * workmem, double * workmem2) const;
208 
209  //Partitioning 3-1-2 (d90 --> d189)
210  void fill_a_S0(TensorT * denT, Tensor3RDM * tofill, TensorS0 * denS0, double * workmem) const;
211  void fill_bcd_S0(TensorT * denT, Tensor3RDM * tofill, TensorS0 * denS0, double * workmem) const;
212  void fill_F0(TensorT * denT, Tensor3RDM * tofill, TensorF0 * denF0, double * workmem) const;
213  void fill_F0_T(TensorT * denT, Tensor3RDM * tofill, TensorF0 * denF0, double * workmem) const;
214  void fill_a_S1(TensorT * denT, Tensor3RDM * doublet, Tensor3RDM * quartet, TensorS1 * denS1, double * workmem, double * workmem2) const;
215  void fill_bcd_S1(TensorT * denT, Tensor3RDM * doublet, Tensor3RDM * quartet, TensorS1 * denS1, double * workmem, double * workmem2) const;
216  void fill_F1(TensorT * denT, Tensor3RDM * doublet, Tensor3RDM * quartet, TensorF1 * denF1, double * workmem, double * workmem2) const;
217  void fill_F1_T(TensorT * denT, Tensor3RDM * doublet, Tensor3RDM * quartet, TensorF1 * denF1, double * workmem, double * workmem2) const;
218 
219  };
220 }
221 
222 #endif
void mpi_allreduce()
Add the 3-RDM elements of all MPI processes.
void save_HAM(const string filename) const
Save the 3-RDM to disk in Hamiltonian indices.
Definition: ThreeDM.cpp:371
void correct_higher_multiplicities()
After the whole 3-RDM is filled, a prefactor for higher multiplicities should be applied.
Definition: ThreeDM.cpp:316
Definition: CASPT2.h:42
ThreeDM(const SyBookkeeper *book_in, const Problem *prob_in, const bool disk_in)
Constructor.
Definition: ThreeDM.cpp:38
static void save_HAM_generic(const string filename, const int LAS, const string tag, double *array)
Generic save routine for objects of size LAS**6.
Definition: ThreeDM.cpp:378
void fill_ham_index(const double alpha, const bool add, double *storage, const int last_orb_start, const int last_orb_num)
Perform storage[ :, :, :, :, :, : ] { = or += } alpha * 3-RDM[ :, :, :, :, :, last_orb_start: last_or...
Definition: ThreeDM.cpp:155
double trace()
Return the trace (should be N(N-1)(N-2))
Definition: ThreeDM.cpp:191
void fill_site(TensorT *denT, TensorL ***Ltens, TensorF0 ****F0tens, TensorF1 ****F1tens, TensorS0 ****S0tens, TensorS1 ****S1tens, Tensor3RDM ****dm3_a_J0_doublet, Tensor3RDM ****dm3_a_J1_doublet, Tensor3RDM ****dm3_a_J1_quartet, Tensor3RDM ****dm3_b_J0_doublet, Tensor3RDM ****dm3_b_J1_doublet, Tensor3RDM ****dm3_b_J1_quartet, Tensor3RDM ****dm3_c_J0_doublet, Tensor3RDM ****dm3_c_J1_doublet, Tensor3RDM ****dm3_c_J1_quartet, Tensor3RDM ****dm3_d_J0_doublet, Tensor3RDM ****dm3_d_J1_doublet, Tensor3RDM ****dm3_d_J1_quartet)
Fill the 3-RDM terms corresponding to site denT->gIndex()
Definition: ThreeDM.cpp:398
double get_ham_index(const int cnt1, const int cnt2, const int cnt3, const int cnt4, const int cnt5, const int cnt6) const
Get a 3-RDM, using the HAM indices.
Definition: ThreeDM.cpp:148
virtual ~ThreeDM()
Destructor.
Definition: ThreeDM.cpp:68