24namespace triqs_cthyb {
26 histogram *move_shift_operator::add_histo(std::string
const &name, histo_map_t *histos) {
27 if (!histos)
return nullptr;
28 auto new_histo = histos->insert({name, {.0, config.beta(), 100}});
29 return &(new_histo.first->second);
32 move_shift_operator::move_shift_operator(qmc_data &data, mc_tools::random_generator &rng, histo_map_t *histos)
36 histo_proposed(add_histo(
"shift_length_proposed", histos)),
37 histo_accepted(add_histo(
"shift_length_accepted", histos)),
40 mc_weight_t move_shift_operator::attempt() {
43 std::cerr <<
">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>" << std::endl;
44 std::cerr <<
"In config " << config.get_id() << std::endl;
45 std::cerr <<
"* Attempt for move_shift_operator ";
50 auto config_size = config.size();
51 if (config_size == 0) {
53 std::cerr <<
"(empty configuration)" << std::endl;
58 const int op_pos_in_config = rng(config_size);
61 auto itconfig = config.begin();
62 for (
int i = 0; i < op_pos_in_config; ++i, ++itconfig)
64 tau_old = (*itconfig).first;
65 op_old = (*itconfig).second;
66 block_index = op_old.block_index;
67 auto is_dagger = op_old.dagger;
70 std::cerr <<
"(block " << block_index <<
")" << std::endl;
74 auto &det = data.dets[block_index];
75 auto det_size = det.size();
76 if (det_size == 0)
return 0;
80 auto inner_new = rng(data.n_inner[block_index]);
81 op_new = op_desc{block_index, inner_new, is_dagger, data.linindex[std::make_pair(block_index, inner_new)]};
88 int ic_dag = 0, ic = 0;
97 for (ic_dag = 0; ic_dag < det_size; ++ic_dag) {
98 if (det.get_x(ic_dag).first < tau_old)
break;
100 for (ic = 0; ic < det_size; ++ic) {
101 if (det.get_y(ic).first < tau_old)
break;
104 op_pos_in_det = (is_dagger ? ic_dag : ic);
108 auto tRdag = (ic_dag != det_size ? det.get_x(ic_dag).first : det.get_x(0).first);
109 auto tRnodag = (ic != det_size ? det.get_y(ic).first : det.get_y(0).first);
111 tR = ((tau_old - tRdag) > (tau_old - tRnodag) ? tRnodag : tRdag);
120 auto tLdag = (ic_dag != 0 ? det.get_x(--ic_dag).first : det.get_x(det_size - 1).first);
121 auto tLnodag = (ic != 0 ? det.get_y(--ic).first : det.get_y(det_size - 1).first);
123 tL = ((tLdag - tau_old) > (tLnodag - tau_old) ? tLnodag : tLdag);
125 tau_new = tR + data.tau_seg.get_random_pt(rng, tL - tR);
131 tau_new = data.tau_seg.get_random_pt(rng);
135 dtau = double(tau_new - tau_old);
136 if (histo_proposed) *histo_proposed << dtau;
139 std::cerr <<
"* Proposing to shift:" << std::endl;
140 std::cerr << op_old <<
" tau = " << tau_old << std::endl;
141 std::cerr <<
" to " << std::endl;
142 std::cerr << op_new <<
" tau = " << tau_new << std::endl;
148 data.imp_trace.try_delete(op_pos_in_det, block_index, is_dagger);
152 data.imp_trace.try_insert(tau_new, op_new);
153 }
catch (rbt_insert_error
const &) {
154 std::cerr <<
"Insert error : recovering ... " << std::endl;
155 data.imp_trace.cancel_delete();
156 data.imp_trace.cancel_insert();
157 std::cerr <<
"Insert error : recovered ... " << std::endl;
164 roll_direction = det_type::None;
168 if ((tau_old > tL) && (tau_new < tL)) roll_direction = (is_dagger ? det_type::Up : det_type::Left);
169 if ((tau_old < tL) && (tau_new > tL)) roll_direction = (is_dagger ? det_type::Down : det_type::Right);
173 auto det_ratio = (is_dagger ? det.try_change_row(op_pos_in_det, {tau_new, op_new.inner_index}) :
174 det.try_change_col(op_pos_in_det, {tau_new, op_new.inner_index}));
177 double random_number = rng.preview();
178 if (random_number == 0.0)
return 0;
179 double p_yee = std::abs(det_ratio / data.atomic_weight);
182 std::tie(new_atomic_weight, new_atomic_reweighting) = data.imp_trace.compute(p_yee, random_number);
183 if (new_atomic_weight == 0.0) {
185 std::cerr <<
"atomic_weight == 0" << std::endl;
189 auto atomic_weight_ratio = new_atomic_weight / data.atomic_weight;
190 if (!isfinite(atomic_weight_ratio))
191 TRIQS_RUNTIME_ERROR <<
"atomic_weight_ratio not finite " << new_atomic_weight <<
" " << data.atomic_weight <<
" "
192 << new_atomic_weight / data.atomic_weight <<
" in config " << config.get_id();
195 mc_weight_t p = atomic_weight_ratio * det_ratio;
198 std::cerr <<
"Trace ratio: " << atomic_weight_ratio <<
'\t';
199 std::cerr <<
"Det ratio: " << det_ratio <<
'\t';
200 std::cerr <<
"Weight: " << p << std::endl;
201 std::cerr <<
"p_yee * newtrace: " << p_yee * new_atomic_weight << std::endl;
207 mc_weight_t move_shift_operator::accept() {
210 data.imp_trace.confirm_shift();
213 config.erase(tau_old);
214 config.insert(tau_new, op_new);
218 data.dets[block_index].complete_operation();
221 data.atomic_weight = new_atomic_weight;
222 data.atomic_reweighting = new_atomic_reweighting;
224 if (histo_accepted) *histo_accepted << dtau;
226 auto result = data.current_sign / data.old_sign * data.dets[block_index].roll_matrix(roll_direction);
229 std::cerr <<
"* Move move_shift_operator accepted" << std::endl;
230 std::cerr <<
"<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<" << std::endl;
231 check_det_sequence(data.dets[block_index], config.get_id());
237 void move_shift_operator::reject() {
240 data.imp_trace.cancel_shift();
241 data.dets[block_index].reject_last_try();
244 std::cerr <<
"* Move move_shift_operator rejected" << std::endl;
245 std::cerr <<
"<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<" << std::endl;
246 if (block_index != -1) check_det_sequence(data.dets[block_index], config.get_id());