1 // 2 // scf.h --- definition of the SCF abstract base class 3 // 4 // Copyright (C) 1996 Limit Point Systems, Inc. 5 // 6 // Author: Edward Seidl <seidl@janed.com> 7 // Maintainer: LPS 8 // 9 // This file is part of the SC Toolkit. 10 // 11 // The SC Toolkit is free software; you can redistribute it and/or modify 12 // it under the terms of the GNU Library General Public License as published by 13 // the Free Software Foundation; either version 2, or (at your option) 14 // any later version. 15 // 16 // The SC Toolkit is distributed in the hope that it will be useful, 17 // but WITHOUT ANY WARRANTY; without even the implied warranty of 18 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 19 // GNU Library General Public License for more details. 20 // 21 // You should have received a copy of the GNU Library General Public License 22 // along with the SC Toolkit; see the file COPYING.LIB. If not, write to 23 // the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. 24 // 25 // The U.S. Government is granted a limited license as per AL 91-7. 26 // 27 28 #ifndef _chemistry_qc_scf_scf_h 29 #define _chemistry_qc_scf_scf_h 30 31 #ifdef __GNUC__ 32 #pragma interface 33 #endif 34 35 #include <util/group/thread.h> 36 37 #include <math/optimize/scextrap.h> 38 39 #include <chemistry/qc/basis/tbint.h> 40 #include <chemistry/qc/wfn/accum.h> 41 #include <chemistry/qc/wfn/obwfn.h> 42 43 namespace sc { 44 45 // ////////////////////////////////////////////////////////////////////////// 46 47 /** The SCF class is the base for all classes that use a self-consistent 48 field procedure to solve an effective one body problem. */ 49 class SCF: public OneBodyWavefunction { 50 protected: 51 int need_vec_; 52 int compute_guess_; 53 54 int keep_guess_wfn_; 55 Ref<OneBodyWavefunction> guess_wfn_; 56 57 int always_use_guess_wfn_; 58 59 Ref<SelfConsistentExtrapolation> extrap_; 60 61 Ref<AccumH> accumdih_; 62 Ref<AccumH> accumddh_; 63 64 int maxiter_; 65 int dens_reset_freq_; 66 int reset_occ_; 67 int local_dens_; 68 size_t storage_; 69 int print_all_evals_; 70 int print_occ_evals_; 71 72 double level_shift_; 73 74 Ref<MessageGrp> scf_grp_; 75 Ref<ThreadGrp> threadgrp_; 76 int local_; 77 78 Ref<TwoBodyInt>* tbis_; // a two body integral evaluator for each thread 79 virtual void init_threads(); 80 virtual void done_threads(); 81 82 // implement the Compute::compute() function 83 virtual void compute(); 84 85 // calculate the scf vector, returning the accuracy 86 virtual double compute_vector(double&, double enuclear); 87 88 // return the DIIS error matrices 89 virtual Ref<SCExtrapError> extrap_error(); 90 91 // calculate the scf gradient 92 virtual void compute_gradient(const RefSCVector&); 93 94 // calculate the scf hessian 95 virtual void compute_hessian(const RefSymmSCMatrix&); 96 97 // saves state and restart information after every checkpoint_freq() 98 // SCF iterations 99 virtual void savestate_iter(int); 100 101 // saves state to the given filename 102 virtual void savestate_to_file(const std::string &filename); 103 std::string previous_savestate_file_; 104 105 // returns the log of the max density element in each shell block 106 signed char * init_pmax(double *); 107 108 // given a matrix, this will convert the matrix to a local matrix if 109 // it isn't one already, and return that local matrix. it will also 110 // set the double* to point to the local matrix's data. 111 enum Access { Read, Write, Accum }; 112 RefSymmSCMatrix get_local_data(const RefSymmSCMatrix&, double*&, Access); 113 114 // create the initial scf vector. either use the eigenvectors in 115 // guess_wfn_, or use a core Hamiltonian guess. Call this with needv 116 // equal to 0 if you expect to call it twice with the same geometry 117 // (eg. when calling from both set_occupations() and init_vector()). 118 virtual void initial_vector(int needv=1); 119 120 // given the total number of density and fock matrices, figure out 121 // how much memory that will require and then set the local_dens_ 122 // variable accordingly 123 void init_mem(int); 124 125 void so_density(const RefSymmSCMatrix& d, double occ, int alp=1); 126 127 // Returns a new'ed allocation vector if it is in the input, 128 // otherwise null. 129 int *read_occ(const Ref<KeyVal> &, const char *name, int nirrep); 130 public: 131 SCF(StateIn&); 132 /** The KeyVal constructor. 133 134 <dl> 135 136 <dt><tt>maxiter</tt><dd> This integer specifies the maximum number 137 of SCF iterations. The default is 40. 138 139 <dt><tt>density_reset_frequency</tt><dd> This integer specifies how 140 often, in term of SCF iterations, \f$\Delta D\f$ will be reset to 141 \f$D\f$. The default is 10. 142 143 <dt><tt>reset_occuptions</tt><dd> Reassign the occupations after 144 each iteration based on the eigenvalues. This only has an effect 145 for molecules with higher than \f$C_1\f$ symmetry. The default is 146 false. 147 148 <dt><tt>level_shift</tt><dd> The default is 0. 149 150 <dt><tt>extrap</tt><dd> This specifies an object of type 151 SelfConsistentExtrapolation. The default is a DIIS object. 152 153 <dt><tt>memory</tt><dd> The amount of memory that each processor 154 may use. The default is 0 (minimal memory use). 155 156 <dt><tt>local_density</tt><dd> If this is true, a local copy of the 157 density and \f$G\f$ matrix will be made on all nodes, even if a 158 distributed matrix specialization is used. The default is true. 159 160 <dt><tt>guess_wavefunction</tt><dd> This specifies the initial 161 guess for the solution to the SCF equations. This can be either a 162 OneBodyWavefunction object or the name of file that contains the 163 saved state of a OneBodyWavefunction object. By default the 164 one-electron hamiltonian will be diagonalized to obtain the initial 165 guess. 166 167 <dt><tt>keep_guess_wavefunction</tt><dd> The guess wavefunction is 168 normally discarded after it is projected. Setting this boolean 169 variable to true will cause the guess to be kept. This is useful 170 when doing frequencies of symmetric molecules by finite 171 displacements, because the wavefunction is lost whenever the 172 molecule is displaced into lower symmetry. 173 174 <dt><tt>always_use_guess_wavefunction</tt><dd> If the orbitals must 175 be recomputed after they have already been computed once, then the 176 old orbitals are used as the initial guess by default. However, if 177 this option is true, then the guess wavefunction will be used, if 178 available. If a guess wavefunction is not available, then a core 179 Hamiltonian guess will be used. If this option is set to true, 180 then keep_guess_wavefunction should also be set to true. 181 182 <dt><tt>print_evals</tt><dd>Takes a boolean value. If true, print 183 all eigenvalues after the SCF procedure converges. Takes a boolean 184 value. The default is false. 185 186 <dt><tt>print_occ_evals</tt><dd>Takes a boolean value. If true, 187 print the occupied eigenvalues after the SCF procedure converges. 188 The default is false. 189 190 </dl> */ 191 SCF(const Ref<KeyVal>&); 192 ~SCF(); 193 194 void save_data_state(StateOut&); 195 196 RefSCMatrix oso_eigenvectors(); 197 RefDiagSCMatrix eigenvalues(); 198 199 int spin_unrestricted(); // return 0 200 201 // return the number of AO Fock matrices needed 202 virtual int n_fock_matrices() const =0; 203 204 // returns the n'th AO Fock matrix 205 virtual RefSymmSCMatrix fock(int) =0; 206 207 // return the effective MO fock matrix 208 virtual RefSymmSCMatrix effective_fock() =0; 209 210 virtual double one_body_energy(); 211 virtual void two_body_energy(double &ec, double &ex); 212 213 void symmetry_changed(); 214 215 void obsolete(); 216 217 void print(std::ostream&o=ExEnv::out0()) const; 218 219 protected: 220 // the following are scratch and are not checkpointed 221 RefSCMatrix oso_scf_vector_; 222 RefSCMatrix oso_scf_vector_beta_; // only used if !spin_restricted 223 RefSymmSCMatrix hcore_; 224 225 // ////////////////////////////////////////////////////////////////////// 226 // pure virtual member functions follow 227 228 // tries to automagically guess the MO occupations 229 virtual void set_occupations(const RefDiagSCMatrix&) =0; 230 231 // ////////////////////////////////////////////////////////////////////// 232 // do setup for SCF calculation 233 virtual void init_vector() =0; 234 virtual void done_vector() =0; 235 236 // calculate new density matrices, returns the rms density difference 237 virtual double new_density() =0; 238 239 // reset density diff matrix and zero out delta G matrix 240 virtual void reset_density() =0; 241 242 // return the scf electronic energy 243 virtual double scf_energy() =0; 244 245 // return the DIIS data matrices 246 virtual Ref<SCExtrapData> extrap_data() =0; 247 248 // form the AO basis fock matrices 249 virtual void ao_fock(double accuracy) =0; 250 251 // ////////////////////////////////////////////////////////////////////// 252 // do setup for gradient calculation 253 virtual void init_gradient() =0; 254 virtual void done_gradient() =0; 255 256 virtual RefSymmSCMatrix lagrangian() =0; 257 virtual RefSymmSCMatrix gradient_density() =0; 258 virtual void two_body_deriv(double*) =0; 259 260 // ////////////////////////////////////////////////////////////////////// 261 // do setup for hessian calculation 262 virtual void init_hessian() =0; 263 virtual void done_hessian() =0; 264 265 private: 266 // This experimental function does SVD of Coulomb matrix 267 // to be used in low-rank reconstruction 268 void svd_product_basis(); 269 }; 270 271 } 272 273 #endif 274 275 // Local Variables: 276 // mode: c++ 277 // c-file-style: "ETS" 278 // End: 279