1 /* Ergo, version 3.8, a program for linear scaling electronic structure
2  * calculations.
3  * Copyright (C) 2019 Elias Rudberg, Emanuel H. Rubensson, Pawel Salek,
4  * and Anastasia Kruchinina.
5  *
6  * This program is free software: you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation, either version 3 of the License, or
9  * (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
18  *
19  * Primary academic reference:
20  * Ergo: An open-source program for linear-scaling electronic structure
21  * calculations,
22  * Elias Rudberg, Emanuel H. Rubensson, Pawel Salek, and Anastasia
23  * Kruchinina,
24  * SoftwareX 7, 107 (2018),
25  * <http://dx.doi.org/10.1016/j.softx.2018.03.005>
26  *
27  * For further information about Ergo, see <http://www.ergoscf.org>.
28  */
29 
30 /** @file SCF_general.h
31 
32     @brief Class for self-consistent field (SCF) procedure; base class
33     that can be used for both restricted and unrestricted cases.
34 
35     @author: Elias Rudberg <em>responsible</em>.
36 */
37 
38 #ifndef SCF_GENERAL_HEADER
39 #define SCF_GENERAL_HEADER
40 
41 #include "molecule.h"
42 #include "basisinfo.h"
43 #include "integrals_2el.h"
44 #include "grid_stream.h"
45 #include "scf.h"
46 #include "diis_general.h"
47 #include "SCF_statistics.h"
48 #include "GetDensFromFock.h"
49 
50 
51 class SCF_general
52 {
53  public:
54 
55   // SCF convergence routine
56   void do_SCF_iterations();
57 
58   void get_overlap_matrix(symmMatrix & S);
59   void get_invCholFactor_matrix(triangMatrix & invCholFactor_);
60   void get_H_core_matrix(symmMatrix & H_core);
61   void get_energy(ergo_real & E, ergo_real & E_nuclear);
62 
63  protected:
64   // Constructor
65   SCF_general(const Molecule& molecule_,
66 	      const Molecule& extraCharges_,
67 	      const BasisInfoStruct & basisInfo_,
68 	      const IntegralInfo & integralInfo_,
69 	      const char* guessDmatFileName_,
70 	      const JK::Params& J_K_params_,
71 	      const Dft::GridParams& gridParams_,
72 	      const SCF::Options& scfopts,
73 	      const SCF::MatOptions& matOpts,
74 	      ergo_real threshold_integrals_1el_input);
75 
76   // Destructor
77   virtual ~SCF_general();
78 
79   const Molecule& molecule;
80   const Molecule& extraCharges;
81   const BasisInfoStruct & basisInfo;
82   const IntegralInfo& integralInfo;
83   const char* guessDmatFileName;
84   const JK::Params& J_K_params;
85   const Dft::GridParams& gridParams;
86   const SCF::Options& scfopts;
87   const SCF::MatOptions& matOpts;
88   ergo_real threshold_integrals_1el;
89 
90   //integral_prep_struct* integralPrep;
91 
92   JK::ExchWeights CAM_params;  // range-separated exchange parameters
93 
94   // number of SCF cycle
95   int SCF_step;
96 
97   // nuclearEnergy is nuclear repulsion energy plus contribution from external electric field.
98   ergo_real nuclearEnergy;
99 
100   ergo_real energy_2el;
101   ergo_real energy;
102 
103   ergo_real energy_2el_core; // only used when "core density matrix" is used
104   ergo_real energy_2el_valence; // only used when "core density matrix" is used
105   ergo_real energy_of_valence; // only used when "core density matrix" is used
106   ergo_real energy_reference; // only used when "core density matrix" is used
107 
108   ergo_real electronicEntropyTerm;
109 
110   ergo_real errorMeasure;
111 
112   ergo_real curr_subspace_diff;
113 
114   symmMatrix S_symm;
115   triangMatrix invCholFactor;
116   ergo_real invCholFactor_euclnorm;
117   symmMatrix H_core_Matrix;
118 
119   DIISManager* DIIS; // Must be initialized by restricted/unrestricted derived class.
120 
121   int noOfElectrons;
122 
123   SCF_statistics* curr_cycle_stats;
124 
125   GetDensFromFock DensFromFock;
126 
127   ergo_real GetEuclideanNormOfMatrix(const symmMatrix & A);
128 
129   virtual void initialize_matrices() = 0;
130   virtual void check_params() = 0;
131   virtual void get_starting_guess_density() = 0;
132   virtual void initialize_homo_lumo_limits() = 0;
133   virtual void write_matrices_to_file() = 0;
134   virtual void get_2e_part_and_energy() = 0;
135   virtual void output_sparsity_S_F_D(SCF_statistics & stats) = 0;
136   virtual void calculate_energy() = 0;
137   virtual void get_FDSminusSDF() = 0;
138   virtual void get_error_measure() = 0;
139   virtual void add_to_DIIS_list() = 0;
140   virtual void update_best_fock_so_far() = 0;
141   virtual void combine_old_fock_matrices(ergo_real stepLength) = 0;
142   virtual void use_diis_to_get_new_fock_matrix() = 0;
143   virtual void clear_diis_list() = 0;
144   virtual void clear_error_matrices() = 0;
145   virtual void save_current_fock_as_fprev() = 0;
146   virtual void get_new_density_matrix() = 0;
147   virtual void write_density_to_file() = 0;
148   virtual void save_final_potential() = 0;
149   virtual void add_random_disturbance_to_starting_guess() = 0;
150   virtual void output_expected_values_pos_operator() = 0;
151   virtual void output_density_images() = 0;
152   virtual void write_diag_dens_to_file() = 0;
153   virtual void report_final_results() = 0;
154   virtual void save_density_as_prevdens() = 0;
155   virtual void update_subspace_diff() = 0;
156   virtual void disturb_fock_matrix(ergo_real subspaceError) = 0;
157   virtual void disturb_dens_matrix(ergo_real subspaceError) = 0;
158   virtual void do_spin_flip(int atomCount) = 0;
159   virtual void disturb_dens_matrix_exact(ergo_real subspaceError) = 0;
160   virtual void save_full_matrices_for_matlab() = 0;
161   virtual void report_density_difference() = 0;
162   virtual void create_mtx_files_F(int const scfIter) = 0;
163   virtual void create_mtx_files_D(int const scfIter) = 0;
164   virtual void create_eigenvectors_files() const = 0;
165   virtual void create_gabedit_file() const = 0;
166   virtual void compute_dipole_moment() = 0;
167   virtual void do_mulliken_pop_stuff() = 0;
168   virtual void compute_gradient_fixeddens() = 0;
169 };
170 
171 
172 
173 
174 
175 #endif
176