High-precision calculations for one- and two-valence atomic systems
MixedStates.hpp
1#pragma once
2#include <vector>
3class Wavefunction;
4class DiracSpinor;
5class Grid;
6namespace MBPT {
7class CorrelationPotential;
8}
9namespace HF {
10class HartreeFock;
11class Breit;
12} // namespace HF
13
14//! External field: Mixed-states + Core Polarisation
15namespace ExternalField {
16
17constexpr bool print_final_eps = false;
18constexpr bool print_each_eps = false;
19
20/*!
21 @brief Solves the inhomogeneous TDHF (mixed-states) equation for perturbed orbital dF.
22 @details
23 Solves
24 \f[
25 (h_{\rm HF} - \en_a \mp \omega)\delta F + F_S = 0
26 \f]
27 for \f$ \delta F \f$, where \f$ F_S \f$ is the source term. Typically
28 \f[
29 F_S = (t_\pm + \delta V_\pm - \delta\en^a_\pm)\phi_a.
30 \f]
31
32 - The angular momentum \f$ \kappa \f$ of the solution is that of @p Fs.
33 - \f$ t \f$: Extenral field operator
34 - \f$ \delta V_\pm \f$: core polarisation correction (see @ref CorePolarisation)
35 - Solved iteratively using the Green's function method.
36
37 @param Fa Unperturbed orbital \f$ \phi_a \f$.
38 @param omega External-field frequency \f$ \omega \f$.
39 @param vl Local potential (nuclear + direct).
40 @param alpha Fine-structure constant.
41 @param core Core electrons (for exchange).
42 @param Fs Source term \f$ F_S \f$ (note sign: this is \f$ h\phi_a \f$,
43 not \f$ -h\phi_a \f$).
44 @param eps_target Convergence goal for the inhomogeneous ODE solver.
45 @param Sigma Optional correlation potential.
46 @param VBr Optional Breit interaction.
47 @param H_mag Magnetic part of QED radiative potential (electric part
48 should be included in @p vl).
49
50 @return Perturbed orbital \f$ \delta F \f$.
51*/
53 const DiracSpinor &Fa, double omega, const std::vector<double> &vl,
54 double alpha, const std::vector<DiracSpinor> &core, const DiracSpinor &Fs,
55 double eps_target = 1.0e-9,
56 const MBPT::CorrelationPotential *const Sigma = nullptr,
57 const HF::Breit *const VBr = nullptr, const std::vector<double> &H_mag = {});
58
59/*!
60 @brief As solveMixedState(), but updates an existing solution @p dF in place.
61 @details
62 Starts from @p dF as an initial guess rather than zero; converges faster if
63 @p dF is already an approximate solution (e.g., from a nearby frequency).
64
65 @note Near-resonant channels are handled automatically: \f$ (h_{\rm HF} -
66 \en_a \mp \omega) \f$ is (near-)singular for components along any same-kappa
67 bound state with \f$ \en_m \approx \en_a \pm \omega \f$ (the diagonal @p Fa,
68 fine-structure partners, etc.). These are projected out of the source,
69 the solution is forced orthogonal to them, and the off-diagonal components are
70 restored analytically. The caller need not pre-condition @p Fs.
71*/
72void solveMixedState(DiracSpinor &dF, const DiracSpinor &Fa, double omega,
73 const std::vector<double> &vl, double alpha,
74 const std::vector<DiracSpinor> &core,
75 const DiracSpinor &Fs, double eps_target = 1.0e-9,
76 const MBPT::CorrelationPotential *const Sigma = nullptr,
77 const HF::Breit *const VBr = nullptr,
78 const std::vector<double> &H_mag = {});
79
80/*!
81 @brief Anderson mixing coefficients for a fixed-point
82 iteration x -> G(x).
83 @details
84 Given the residuals \f$ r_k = G(x_k) - x_k \f$ of the stored iterates
85 (oldest first) through their Gram matrix \f$ B_{kl} = \braket{r_k}{r_l} \f$,
86 returns the \f$ c_k \f$ minimising
87 \f[ \Big\|\sum_k c_k r_k\Big\|^2 \quad\text{subject to}\quad \sum_k c_k = 1, \f]
88 via the bordered system [B 1; 1^T 0][c; lambda] = [0; 1]. The next iterate
89 is \f$ x = \sum_k c_k G(x_k) \f$. For a linear map this is equivalent to
90 (truncated) GMRES: it converges wherever the linear problem is
91 non-singular, where damped iteration may not.
92
93 A saturated history makes B ill-conditioned: the oldest entries are then
94 dropped, and the returned vector holds one coefficient per KEPT entry, the
95 last c.size() entries of the history (the caller drops the same entries
96 from its own history). Empty if no entry is usable (take a plain step).
97*/
98std::vector<double>
99anderson_coefficients(const std::vector<std::vector<double>> &gram);
100
101//! As above, from the residual spinors directly (Gram matrix of their inner
102//! products).
103std::vector<double>
104anderson_coefficients(const std::vector<DiracSpinor> &residuals);
105
106/*!
107 @brief Bound mixed-state solve with Anderson acceleration; the bound
108 channels of @ref TDHFcntm.
109 @details
110 Same physics and conditioning as @ref solveMixedState (in-place overload),
111 but the linear equation \f$ (h_{\rm HF} - \en_0)\,\delta F = -F_S \f$ is
112 solved by Anderson mixing (@ref anderson_coefficients) of the preconditioned
113 fixed-point map instead of damped iteration. At the high frequencies of
114 ionisation a bound channel's \f$ \en_0 = \en_a + \omega \f$ can sit near a
115 spurious eigenvalue of the local preconditioner
116 \f$ (h_{\rm local} + U_x - \en_0) \f$, where damped iteration diverges
117 although \f$ (h_{\rm HF} - \en_0) \f$ is non-singular; Anderson mixing
118 converges on the conditioning of the true operator. Parameters as
119 @ref solveMixedState.
120*/
121void solveMixedState_cntm(DiracSpinor &dF, const DiracSpinor &Fa, double omega,
122 const std::vector<double> &vl, double alpha,
123 const std::vector<DiracSpinor> &core,
124 const DiracSpinor &Fs, double eps_target = 1.0e-9,
125 const HF::Breit *const VBr = nullptr,
126 const std::vector<double> &H_mag = {});
127
128/*!
129 @brief Continuum (en_+ > 0) mixed-state solve with the standing-wave
130 boundary condition and the non-local exchange iterated in the source: the
131 open channels of @ref TDHFcntm.
132 @details
133 Solves
134 \f[
135 (h_r^{(\kappa)} + V^{\rm nl} - \en_+)\,\varphi = -F_S ,
136 \qquad
137 \en_+ = \en_a + \omega > 0 ,
138 \f]
139 with \f$ \varphi \to K\,F_{\rm irr} \f$ at large r, by outward integration
140 plus F_reg subtraction (@ref DiracODE::solveContinuumForward) on the two
141 real homogeneous solutions at en_+: the regular, energy-normalised
142 continuum orbital F_reg and its irregular partner F_irr
143 (@ref DiracODE::solveContinuumIrregular), in the local potential
144 \f$ v = v_l + U_x \f$, with \f$ U_x \f$ the orbital-independent Kohn-Sham
145 exchange (@ref HF::vex_KS) for conditioning (cancelled in the source at the
146 fixed point). The non-local exchange remainder is iterated in the source
147 with Anderson mixing (@ref anderson_coefficients); K is linear in phi and
148 is mixed with the same coefficients. After each solve, phi is
149 orthogonalised to Fa when the channel shares its kappa (norm conservation,
150 as the bound solver); other occupied components are kept, since their dV
151 contributions cancel pairwise across channels.
152
153 The hole-particle treatment is the caller's: pass @p vl already adjusted
154 (\f$ v_l - y^0_{aa} \f$) and the hole orbital as @p Fhole, so that the
155 iterated exchange is \f$ V^{\rm exch} - X_a \f$ (@ref HF::vexFa_1el);
156 together these put the ejected electron in the V^{N-1} Hamiltonian (do
157 both or neither).
158
159 If @p Freg already holds the pair at en_+ (Freg->en() == en_+, nonzero),
160 the homogeneous solutions are reused (they depend only on the channel and
161 omega); otherwise they are built and written.
162
163 @param phi In/out: the correction orbital (kappa = channel kappa, as
164 @p Fs). Used as the starting guess if nonzero.
165 @param Freg In/out: regular energy-normalised continuum orbital at en_+.
166 @param Firr In/out: irregular partner.
167 @param K Output (if non-null): standing-wave amplitude, phi -> K F_irr.
168 @param Fa Core orbital phi_a (energy and grid).
169 @param omega Frequency (en_+ = Fa.en() + omega must be > 0).
170 @param vl Local potential (including any hole-particle term).
171 @param alpha Fine-structure constant.
172 @param core Core orbitals (exchange).
173 @param Fs Source spinor F_S (sign as solveMixedState: +h phi_a).
174 @param eps_target Convergence goal of the exchange iteration.
175 @param Fhole Optional hole orbital (V^{N-1} exchange part).
176
177 @warning Requires en_+ > 0 and a grid dense enough at large r; a reused
178 pair must have been built in the same local potential (not
179 checked).
180*/
182 DiracSpinor *Firr, double *K,
183 const DiracSpinor &Fa, double omega,
184 const std::vector<double> &vl, double alpha,
185 const std::vector<DiracSpinor> &core,
186 const DiracSpinor &Fs, double eps_target = 1.0e-9,
187 const DiracSpinor *const Fhole = nullptr);
188
189//! Solves Mixed States (TDHF) equation. Overload; takes hf object
191solveMixedState(const DiracSpinor &Fa, double omega, const DiracSpinor &Fs,
192 const HF::HartreeFock *const hf, double eps_target = 1.0e-9,
193 const MBPT::CorrelationPotential *const Sigma = nullptr);
194
195//! Solves Mixed States (TDHF) equation. Overload; takes hf object
196void solveMixedState(DiracSpinor &dF, const DiracSpinor &Fa, double omega,
197 const DiracSpinor &Fs, const HF::HartreeFock *const hf,
198 double eps_target = 1.0e-9,
199 const MBPT::CorrelationPotential *const Sigma = nullptr);
200
201/*!
202 @brief Solves for dF via explicit sum over basis; mainly for tests.
203 @details
204 \f[
205 \delta F = \sum_n \frac{\ket{n}\matel{n}{F_S}{a}}{\en_a - \en_n \pm \omega}
206 \f]
207 where @p hFa is the already-evaluated source spinor \f$ F_S \f$.
208*/
210 double omega,
211 const std::vector<DiracSpinor> &basis);
212
213/*!
214 @brief Find bound states of the solve channel that make (h_l - e0) near-singular.
215 @details
216 For the channel of kappa @p kappa and energy \f$ e_0 = \en_a \pm \omega \f$,
217 the radial operator \f$ (h_l - e_0) \f$ is (near-)singular for components
218 along any bound core state \f$ \phi_m \f$ of the same kappa with
219 \f$ \en_m \approx e_0 \f$: exactly singular for the diagonal (\f$ \phi_a \f$,
220 \f$ \omega = 0 \f$) case, near-singular for e.g. fine-structure partners.
221 Those components cannot be resolved reliably by the Green's-function solve, so
222 they are projected out of the source (forces the solution orthogonal
223 to them), they should be restore the off-diagonal ones analytically afterwards.
224
225 The set is the same-kappa core states satisfying a relative nearness criterion
226 \f$ |e_0 - \en_m| < \eta\,|e_0 + \en_m| \f$ (\f$ \eta = 0.2 \f$), plus @p Fa
227 itself when it shares the channel kappa (the \f$ \matel{a}{\delta F}{} = 0 \f$
228 / left-orthogonality constraint).
229*/
230std::vector<const DiracSpinor *>
231conditioning_states(const std::vector<DiracSpinor> &core, const DiracSpinor &Fa,
232 int kappa, double e0);
233
234} // namespace ExternalField
Stores radial Dirac spinor: F_nk = (f, g)
Definition DiracSpinor.hpp:44
Non-uniform radial grid with Jacobian, suitable for atomic structure calculations.
Definition Grid.hpp:85
Breit potentials for one- (Hartree-Fock Breit) and two-body Breit integrals.
Definition Breit.hpp:88
Solves relativistic Hartree-Fock equations for core and valence. Optionally includes Breit and QED ef...
Definition HartreeFock.hpp:111
Stores Wavefunction (set of valence orbitals, grid, HF etc.)
Definition Wavefunction.hpp:38
Core-polarisation (RPA) corrections to matrix elements of an external field.
Definition MatrixElements.hpp:9
void solveContinuumMixedState(DiracSpinor *phi, DiracSpinor *Freg, DiracSpinor *Firr, double *K, const DiracSpinor &Fa, const double omega, const std::vector< double > &vl, const double alpha, const std::vector< DiracSpinor > &core, const DiracSpinor &Fs, const double eps_target, const DiracSpinor *const Fhole)
Continuum (en_+ > 0) mixed-state solve with the standing-wave boundary condition and the non-local ex...
Definition MixedStates.cpp:331
void solveMixedState_cntm(DiracSpinor &dF, const DiracSpinor &Fa, const double omega, const std::vector< double > &vl, const double alpha, const std::vector< DiracSpinor > &core, const DiracSpinor &hFa, const double eps_target, const HF::Breit *const VBr, const std::vector< double > &H_mag)
Bound mixed-state solve with Anderson acceleration; the bound channels of TDHFcntm.
Definition MixedStates.cpp:223
std::vector< const DiracSpinor * > conditioning_states(const std::vector< DiracSpinor > &core, const DiracSpinor &Fa, int kappa, double e0)
Find bound states of the solve channel that make (h_l - e0) near-singular.
Definition MixedStates.cpp:22
DiracSpinor solveMixedState(const DiracSpinor &Fa, double omega, const std::vector< double > &vl, double alpha, const std::vector< DiracSpinor > &core, const DiracSpinor &hFa, double eps_target, const MBPT::CorrelationPotential *const Sigma, const HF::Breit *const VBr, const std::vector< double > &H_mag)
Solves the inhomogeneous TDHF (mixed-states) equation for perturbed orbital dF.
Definition MixedStates.cpp:44
DiracSpinor solveMixedState_basis(const DiracSpinor &Fa, const DiracSpinor &hFa, double omega, const std::vector< DiracSpinor > &basis)
Solves for dF via explicit sum over basis; mainly for tests.
Definition MixedStates.cpp:500
std::vector< double > anderson_coefficients(const std::vector< std::vector< double > > &gram)
Anderson mixing coefficients for a fixed-point iteration x -> G(x).
Definition MixedStates.cpp:169
Functions and classes for Hartree-Fock.
Definition CI_Integrals.hpp:16
Many-body perturbation theory.
Definition MatrixElements.hpp:12
void Breit(const IO::InputBlock &input, const Wavefunction &wf)
Breit corrections to HF energies.
Definition Breit.cpp:44