24#include <triqs/utility/itertools.hpp>
28namespace triqs_cthyb {
30 using namespace G2_iw;
32 template <G2_channel Channel>
33 measure_G2_iw<Channel>::measure_G2_iw(std::optional<G2_iw_t> &G2_iw_opt, qmc_data
const &data,
35 : measure_G2_iw_base<Channel>(G2_iw_opt, data, G2_measures) {
38 for (
auto const &m : M) {
39 auto norb1 =
static_cast<size_t>(m.target_shape()[0]);
40 auto norb2 =
static_cast<size_t>(m.target_shape()[1]);
41 size_t nfreq_pts =
static_cast<size_t>(std::get<0>(M_mesh.components()).size());
42 M_block_arr.push_back(M_arr_t(norb1, norb2, nfreq_pts, nfreq_pts));
46 template <G2_channel Channel>
void measure_G2_iw<Channel>::accumulate(mc_weight_t s) {
55 auto M_ww_fill = [
this](det_type
const &det, M_t &M_ww) {
56 const double beta = this->data.config.beta();
57 foreach (det, [&M_ww, beta](op_t
const &x, op_t
const &y, det_scalar_t M_xy) {
59 double t1 = double(x.first);
60 double t2 = double(y.first);
61 for (
auto [w1, w2] : M_ww.mesh()) { M_ww[w1, w2](x.second, y.second) += exp((beta - t1) * w1) * M_xy * std::exp(t2 * w2); }
69 for (
auto bidx : range(M.size())) { M_ww_fill(data.dets[bidx], M[bidx]); }
81 template <G2_channel Channel>
void measure_G2_iw<Channel>::accumulate_M_opt() {
87 const double beta = data.config.beta();
88 const double pi_beta = M_PI / beta;
90 auto M_arr_fill = [pi_beta, beta](det_type
const &det, M_arr_t &M_arr, M_mesh_t
const &M_mesh) {
92 [&M_mesh, &M_arr, pi_beta, beta](op_t
const &x, op_t
const &y, det_scalar_t M_xy) {
93 double t1 = double(x.first);
94 double t2 = double(y.first);
96 const auto &mesh1 = std::get<0>(M_mesh.components());
97 const auto &mesh2 = std::get<1>(M_mesh.components());
99 std::complex<double> dWt1(0., 2 * pi_beta * (beta - t1));
100 std::complex<double> dWt2(0., 2 * pi_beta * t2);
102 auto dexp1 = std::exp(dWt1);
103 auto dexp2 = std::exp(dWt2);
105 auto exp1 = std::exp(dWt1 * (mesh1.first_index() + 0.5));
107 for (
auto const i1 : range(M_arr.shape()[2])) {
109 auto exp2 = std::exp(dWt2 * (mesh2.first_index() + 0.5));
110 auto exp1_M_xy = exp1 * M_xy;
112 for (
auto const i2 : range(M_arr.shape()[3])) {
114 M_arr(x.second, y.second, i1, i2) += exp1_M_xy * exp2;
126 for (
auto bidx : range(M_block_arr.size())) {
127 M_block_arr[bidx]() = 0;
128 M_arr_fill(data.dets[bidx], M_block_arr[bidx], M_mesh);
132 for (
auto bidx : range(M_block_arr.size()))
133 for (
auto [n1, n2, i, j] : product_range(M[bidx].data().shape()))
134 M[bidx].data()(n1, n2, i, j) = M_block_arr[bidx](i, j, n1, n2);
139 template class measure_G2_iw<G2_channel::AllFermionic>;
140 template class measure_G2_iw<G2_channel::PP>;
141 template class measure_G2_iw<G2_channel::PH>;