votca 2026-dev
Loading...
Searching...
No Matches
vxc_potential.h
Go to the documentation of this file.
1/*
2 * Copyright 2009-2020 The VOTCA Development Team
3 * (http://www.votca.org)
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License")
6 *
7 * You may not use this file except in compliance with the License.
8 * You may obtain a copy of the License at
9 *
10 * http://www.apache.org/licenses/LICENSE-2.0
11 *
12 * Unless required by applicable law or agreed to in writing, software
13 * distributed under the License is distributed on an "AS IS" BASIS,
14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 * See the License for the specific language governing permissions and
16 * limitations under the License.
17 *
18 */
19
20#pragma once
21#ifndef VOTCA_XTP_VXC_POTENTIAL_H
22#define VOTCA_XTP_VXC_POTENTIAL_H
23
24#include <xc.h>
25
26#include <array>
27#include <vector>
28
29#include "grid_containers.h"
30#include "gridbox.h"
31
32#undef LOG
33
34namespace votca {
35namespace xtp {
36
37class AOBasis;
38class QMMolecule;
39
40template <class Grid>
42 public:
43 struct SpinResult {
44 double energy = 0.0;
45 Eigen::MatrixXd vxc_alpha;
46 Eigen::MatrixXd vxc_beta;
47 };
48
49 explicit Vxc_Potential(const Grid& grid) : grid_(grid) {};
51
52 static double getExactExchange(const std::string& functional);
53 void setXCfunctional(const std::string& functional);
54
55 Mat_p_Energy IntegrateVXC(const Eigen::MatrixXd& density_matrix) const;
56
62 std::vector<Eigen::MatrixXd> IntegrateFXC(
63 const Eigen::MatrixXd& density_matrix,
64 const std::vector<Eigen::MatrixXd>& response_matrices) const;
65 SpinResult IntegrateVXCSpin(const Eigen::MatrixXd& dmat_alpha,
66 const Eigen::MatrixXd& dmat_beta) const;
67
74 std::vector<std::array<Eigen::MatrixXd, 2>> IntegrateFXCSpin(
75 const Eigen::MatrixXd& dmat_alpha, const Eigen::MatrixXd& dmat_beta,
76 const std::vector<std::array<Eigen::MatrixXd, 2>>& response) const;
77
78 // ===========================================================================
79 // XC nuclear gradient at fixed density matrix, part 1: basis-function
80 // (Pulay) and grid-point translation terms, for LDA and GGA (the GGA sigma
81 // terms use AOShell::EvalAOspaceHessian and vanish for LDA, where
82 // df_dsigma stays 0). Despite the name it computes both terms, which
83 // share one AO evaluation per grid point. Derivation in vxc_potential.cc.
84 // ===========================================================================
85 Eigen::MatrixXd PulayGradient(const Eigen::MatrixXd& density_matrix,
86 const AOBasis& dftbasis) const;
87
88 // ===========================================================================
89 // XC nuclear gradient, part 2: derivative of the SSW grid weights. Only the
90 // sum PulayGradient + GridWeightGradient equals the derivative of the XC
91 // energy of IntegrateVXC (checked by finite differences in
92 // test_xcgradient.cc). Cost is O(Natoms^3) per grid point, one power of
93 // Natoms more than the SSW partition itself.
94 // ===========================================================================
95 Eigen::MatrixXd GridWeightGradient(const Eigen::MatrixXd& density_matrix,
96 const QMMolecule& atoms) const;
97
98 // ===========================================================================
99 // UKS (spin-polarized) analogs of PulayGradient/GridWeightGradient
100 // above, for LDA and GGA.
101 //
102 // Basis-type and translation-type rho terms, for each spin channel
103 // s in {a,b}:
104 // d(rho_s,p)/dR_A|_basis = -2 * sum_{mu in A} temp_s,mu * grad(chi_mu)
105 // d(rho_s,p)/dR_A|_translation = grad_s,p if A == owner(p), else 0
106 // with temp_s = dmat_s * ao.values and grad_s = 2*(ao.derivatives^T *
107 // temp_s), as in IntegrateVXCSpin (UKS spin density matrices are not
108 // doubled, unlike DMAT_here = 2*P for RKS), contracted with vrho_a/vrho_b
109 // and summed over both spins.
110 //
111 // GGA: the three sigma_aa/sigma_ab/sigma_bb terms reduce to the per-spin
112 // machinery of the restricted GGA case (Gmat_s, Hessian_rho_s) applied
113 // once per spin, with the effective gradient vectors
114 // V_a = 2*vsigma_aa*rho_a_grad + vsigma_ab*rho_b_grad
115 // V_b = 2*vsigma_bb*rho_b_grad + vsigma_ab*rho_a_grad
116 // Basis-type sigma contribution per mu in A:
117 // -[grad(chi_mu)*(Gmat_a.V_a)_mu + temp_a,mu*(Hessian_mu.V_a)
118 // + grad(chi_mu)*(Gmat_b.V_b)_mu + temp_b,mu*(Hessian_mu.V_b)]
119 // Translation-type sigma contribution (A==owner(p) only):
120 // Hessian_rho_a . V_a + Hessian_rho_b . V_b
121 // where Gmat_s = 2*dmat_s*ao.derivatives and Hessian_rho_s is the
122 // restricted Hessian_rho per spin channel.
123 //
124 // The weight-derivative term uses the same dw/dR as GridWeightGradient;
125 // only the energy density changes to (rho_a+rho_b)*f_xc, evaluated with
126 // sigma_aa/sigma_ab/sigma_bb from the density gradients, as in the energy
127 // of IntegrateVXCSpin.
128 Eigen::MatrixXd PulayGradientUKS(const Eigen::MatrixXd& dmat_alpha,
129 const Eigen::MatrixXd& dmat_beta,
130 const AOBasis& dftbasis) const;
131 Eigen::MatrixXd GridWeightGradientUKS(const Eigen::MatrixXd& dmat_alpha,
132 const Eigen::MatrixXd& dmat_beta,
133 const QMMolecule& atoms) const;
134 // ===========================================================================
135
136 private:
137 struct XC_entry {
138 double f_xc = 0;
139 double df_drho = 0;
140 double df_dsigma = 0;
141 };
142
144 double f_xc = 0;
145 double vrho_a = 0;
146 double vrho_b = 0;
147 double vsigma_aa = 0;
148 double vsigma_ab = 0;
149 double vsigma_bb = 0;
150 };
151
152 XC_entry EvaluateXC(double rho, double sigma) const;
153 XC_entry_spin EvaluateXCSpin(double rho_a, double rho_b, double sigma_aa,
154 double sigma_ab, double sigma_bb) const;
155
156 // libxc for n points at once, exchange and correlation summed. Unpolarized:
157 // rho, sigma, exc, vrho, vsigma have n entries. Polarized (libxc layout):
158 // rho and vrho 2n, sigma and vsigma 3n, exc n. vsigma is zero for LDA.
159 void EvaluateXCBatch(Index n, const double* rho, const double* sigma,
160 double* exc, double* vrho, double* vsigma) const;
161 void EvaluateXCSpinBatch(Index n, const double* rho, const double* sigma,
162 double* exc, double* vrho, double* vsigma) const;
163 // first and second derivatives for n points, unpolarized, exchange and
164 // correlation summed; vsigma, v2rhosigma, v2sigma2 are zero for LDA
165 void EvaluateFXCBatch(Index n, const double* rho, const double* sigma,
166 double* vsigma, double* v2rho2, double* v2rhosigma,
167 double* v2sigma2) const;
168 // the same, polarized (libxc layout): rho 2n, sigma and vsigma 3n,
169 // v2rho2 3n (aa, ab, bb), v2rhosigma 6n (a_aa, a_ab, a_bb, b_aa, b_ab,
170 // b_bb), v2sigma2 6n (aa_aa, aa_ab, aa_bb, ab_ab, ab_bb, bb_bb)
171 void EvaluateFXCSpinBatch(Index n, const double* rho, const double* sigma,
172 double* vsigma, double* v2rho2, double* v2rhosigma,
173 double* v2sigma2) const;
174
175 // Grid points processed together inside a box.
176 static constexpr Index kPointBlock = 128;
177
178 const Grid grid_;
180 bool setXC_ = false;
183 xc_func_type xfunc;
184 xc_func_type cfunc;
185 // Polarized handles for the UKS path, set up once with the unpolarized
186 // ones instead of per grid point.
187 xc_func_type xfunc_pol_;
188 xc_func_type cfunc_pol_;
189 bool is_gga_ = false;
190};
191
192} // namespace xtp
193} // namespace votca
194#endif // VOTCA_XTP_VXC_POTENTIAL_H
Container to hold Basisfunctions for all atoms.
Definition aobasis.h:42
static constexpr Index kPointBlock
void EvaluateXCSpinBatch(Index n, const double *rho, const double *sigma, double *exc, double *vrho, double *vsigma) const
Eigen::MatrixXd GridWeightGradient(const Eigen::MatrixXd &density_matrix, const QMMolecule &atoms) const
Eigen::MatrixXd PulayGradient(const Eigen::MatrixXd &density_matrix, const AOBasis &dftbasis) const
void EvaluateFXCSpinBatch(Index n, const double *rho, const double *sigma, double *vsigma, double *v2rho2, double *v2rhosigma, double *v2sigma2) const
XC_entry_spin EvaluateXCSpin(double rho_a, double rho_b, double sigma_aa, double sigma_ab, double sigma_bb) const
void EvaluateXCBatch(Index n, const double *rho, const double *sigma, double *exc, double *vrho, double *vsigma) const
Eigen::MatrixXd PulayGradientUKS(const Eigen::MatrixXd &dmat_alpha, const Eigen::MatrixXd &dmat_beta, const AOBasis &dftbasis) const
XC_entry EvaluateXC(double rho, double sigma) const
void EvaluateFXCBatch(Index n, const double *rho, const double *sigma, double *vsigma, double *v2rho2, double *v2rhosigma, double *v2sigma2) const
Mat_p_Energy IntegrateVXC(const Eigen::MatrixXd &density_matrix) const
void setXCfunctional(const std::string &functional)
std::vector< std::array< Eigen::MatrixXd, 2 > > IntegrateFXCSpin(const Eigen::MatrixXd &dmat_alpha, const Eigen::MatrixXd &dmat_beta, const std::vector< std::array< Eigen::MatrixXd, 2 > > &response) const
Vxc_Potential(const Grid &grid)
static double getExactExchange(const std::string &functional)
std::vector< Eigen::MatrixXd > IntegrateFXC(const Eigen::MatrixXd &density_matrix, const std::vector< Eigen::MatrixXd > &response_matrices) const
Eigen::MatrixXd GridWeightGradientUKS(const Eigen::MatrixXd &dmat_alpha, const Eigen::MatrixXd &dmat_beta, const QMMolecule &atoms) const
SpinResult IntegrateVXCSpin(const Eigen::MatrixXd &dmat_alpha, const Eigen::MatrixXd &dmat_beta) const
Provides a means for comparing floating point numbers.
Definition basebead.h:33
Eigen::Index Index
Definition types.h:26
double vsigma_ab
double vrho_b
double vrho_a
double vsigma_aa
double vsigma_bb
double f_xc
double f_xc
double df_dsigma
double df_drho