17 auto upfold_self_energy_all_freq(one_body_elements_on_grid
const &obe, downfolding_projector
const &Proj,
auto const &Sigma_w,
long k_idx,
19 auto N_nu = obe.H.N_nu(sigma_idx, k_idx);
20 auto n_w = Sigma_w(0, 0).mesh().size();
21 auto out = nda::zeros<dcomplex>(n_w, N_nu, N_nu);
24 auto P = Proj.P(sigma_idx, k_idx)(R, r_all);
25 auto Pdag = dagger(P);
26 auto Sigma_blk = Sigma_w(alpha, sigma_idx).data();
29 for (
auto n : range(n_w)) { out(n, r_all, r_all) += Pdag * nda::matrix<dcomplex>{Sigma_blk(n, r_all, r_all)} * P; }
37 block2_gf<mesh::refreq, matrix_valued>
const &Sigma_w,
double broadening) {
38 using nda::linalg::inv;
40 auto const &mesh = Sigma_w(0, 0).mesh();
42 auto n_k = obe_theta.
H.
n_k();
44 auto n_w = mesh.size();
46 auto delta = im * broadening;
51 for (
auto k_idx : range(n_k)) {
52 for (
auto sigma : range(n_sigma)) {
53 auto P = obe_theta.
P.
P(sigma, k_idx);
54 auto Pdag = dagger(P);
55 auto H_k = obe_theta.
H.
H(sigma, k_idx);
59 auto PSP_all = detail::upfold_self_energy_all_freq(obe_theta, Proj, Sigma_w, k_idx, sigma);
61 for (
auto &&[n, w] : enumerate(mesh)) {
62 auto G_k = nda::matrix<dcomplex>{inv(w + delta + mu - H_k - PSP_all(n,
r_all,
r_all))};
63 gloc_result(0, sigma).data()(n,
r_all,
r_all) += w_k * (P * G_k * Pdag);
71 auto total = nda::zeros<double>(n_sigma, n_w);
72 auto per_theta = nda::zeros<double>(n_sigma, n_w, n_M, n_M);
74 for (
auto sigma : range(n_sigma)) {
75 auto const &G = gloc_result(0, sigma).data();
76 for (
auto &&[n, w] : enumerate(mesh)) {
77 auto g = nda::matrix<dcomplex>{G(n,
r_all,
r_all)};
78 total(sigma, n) = (-1.0 / M_PI) * imag(trace(g));
79 per_theta(sigma, n,
r_all,
r_all) = real(im * (g - dagger(g)) / (2 * M_PI));
83 return {.total = total, .per_theta = per_theta};
88 using nda::linalg::inv;
90 auto const &mesh = Sigma_w(0, 0).mesh() | tl::to<std::vector>();
92 auto n_k = obe.
H.
n_k();
93 auto n_w = mesh.size();
94 auto n_bands = obe.
H.
N_nu(0, 0);
95 auto delta =
dcomplex(0, broadening);
97 auto data = nda::zeros<double>(n_sigma, n_w, n_bands, n_bands);
99 for (
auto k_idx : range(n_k)) {
100 for (
auto sigma : range(n_sigma)) {
101 auto H_k = obe.
H.
H(sigma, k_idx);
104 auto PSP_all = detail::upfold_self_energy_all_freq(obe, obe.
P, Sigma_w, k_idx, sigma);
106 for (
auto &&[n, w] : enumerate(mesh)) {
107 auto G_k = inv(w + delta + mu - H_k - PSP_all(n,
r_all,
r_all));
108 auto A_k = real(
dcomplex(0, 1.0) * (G_k - dagger(G_k)) / (2.0 * M_PI));
109 data(sigma, n,
r_all,
r_all) += k_weight * A_k;
118 block2_gf<mesh::refreq, matrix_valued>
const &Sigma_w,
double broadening) {
119 using nda::linalg::inv;
121 auto const &mesh = Sigma_w(0, 0).mesh() | tl::to<std::vector>();
123 auto n_w = mesh.size();
124 auto n_k = obe.
H.
n_k();
126 auto delta =
dcomplex(0, broadening);
128 auto data = nda::zeros<double>(n_sigma, n_k, n_w);
129 auto proj_data = nda::zeros<double>(n_sigma, n_k, n_w, n_M, n_M);
131#pragma omp parallel for default(none) shared(n_k, n_sigma, n_w, obe, mu, delta, Sigma_w, broadening, mesh, data, proj_data, r_all)
132 for (
auto k_idx : range(n_k)) {
133 for (
auto sigma : range(n_sigma)) {
134 auto P = obe.
P.
P(sigma, k_idx);
135 auto Pdag = dagger(P);
136 auto H_k = obe.
H.
H(sigma, k_idx);
139 auto PSP_all = detail::upfold_self_energy_all_freq(obe, obe.
P, Sigma_w, k_idx, sigma);
141 for (
auto &&[n, w] : enumerate(mesh)) {
142 auto G_k = inv(w + delta + mu - H_k - PSP_all(n,
r_all,
r_all));
145 data(sigma, k_idx, n) = (-1.0 / M_PI) * imag(trace(G_k));
148 auto PGP = P * nda::matrix<dcomplex>{G_k} * Pdag;
149 proj_data(sigma, k_idx, n,
r_all,
r_all) = (-1.0 / M_PI) * imag(PGP);
154 return {.data = data, .proj_data = proj_data};
long n_sigma() const
Dimension of the index.
long dim() const
Dimension of the correlated space.
C2PY_IGNORE gf_struct2_t Gc_block_shape() const
Shape of the Green function in the correlated space, without block decomposition.
std::vector< long > atomic_decomposition() const
Dimensions of each atomic shell, in order.
nda::array< double, 4 > spectral_function(one_body_elements_on_grid const &obe, double mu, block2_gf< mesh::refreq, matrix_valued > const &Sigma_w, double broadening)
Compute the k-summed band-resolved spectral function matrix.
spectral_function_w projected_spectral_function(one_body_elements_on_grid const &obe_theta, downfolding_projector const &Proj, double mu, block2_gf< mesh::refreq, matrix_valued > const &Sigma_w, double broadening)
Compute the atom- and orbital-resolved spectral function (interacting density of states).
spectral_function_kw spectral_function_on_high_symmetry_path(one_body_elements_on_grid const &obe, double mu, block2_gf< mesh::refreq, matrix_valued > const &Sigma_w, double broadening)
Compute momentum-resolved spectral function along high-symmetry path.
gf_struct2_t get_struct(block2_gf< Mesh, matrix_valued > const &g)
block2_gf< Mesh, matrix_valued > make_block2_gf(Mesh const &mesh, gf_struct2_t const &gf_s)
static constexpr auto r_all
generator< std::pair< long, nda::range > > enumerated_sub_slices(auto sub_div)
std::complex< double > dcomplex
nda::array< double, 1 > k_weights
Weight in the BZ for each k-point.
long n_k() const
Number of k-points in the grid.
long N_nu(long sigma, long k_idx) const
Number of bands for a given k-point and spin .
nda::matrix_const_view< dcomplex > H(long sigma, long k_idx) const
Get for a given and .
The projector that downfolds the energy bands onto a set of localized atomic-like orbitals.
nda::matrix_const_view< dcomplex > P(long sigma, long k_idx) const
Get for a given and .
A one-body elements struct where all of the underlying data exists on a fixed momentum grid.
std::optional< ibz_symmetry_ops > ibz_symm_ops
IBZ symmetrizer after a k-sum.
local_space C_space
Local space.
band_dispersion H
Band dispersion.
downfolding_projector P
Downfolding projector .
Returns Tr (A) [σ,k,ω] for all k points in obe grid and all omega in Sigma mesh.
Store data of spectral functions.