25#ifndef __ANDERSON_MIXER_HPP__
26#define __ANDERSON_MIXER_HPP__
64template <
typename... FUNCS>
70 double beta_scaling_factor_;
73 std::size_t history_size_;
75 Anderson(std::size_t max_history,
double beta,
double beta0,
double beta_scaling_factor)
76 :
Mixer<FUNCS...>(max_history)
79 , beta_scaling_factor_(beta_scaling_factor)
80 , S_(max_history - 1, max_history - 1)
81 , S_factorized_(max_history - 1, max_history - 1)
86 void mix_impl()
override
88 const auto idx_step = this->idx_hist(this->step_);
89 const auto idx_next_step = this->idx_hist(this->step_ + 1);
90 const auto idx_prev_step = this->idx_hist(this->step_ - 1);
92 const auto history_size =
static_cast<int>(this->history_size_);
94 const bool normalize =
false;
97 if (this->step_ > this->max_history_) {
98 const double rmse_avg = std::accumulate(this->rmse_history_.begin(), this->rmse_history_.end(), 0.0) /
99 this->rmse_history_.size();
100 if (this->rmse_history_[idx_step] > rmse_avg) {
101 this->beta_ = std::max(beta0_, this->beta_ * beta_scaling_factor_);
108 this->copy(this->output_history_[idx_step], this->input_);
111 this->axpy(this->beta_, this->residual_history_[idx_step], this->input_);
113 if (history_size > 0) {
117 this->scale(-1.0, this->residual_history_[idx_prev_step]);
118 this->axpy(1.0, this->residual_history_[idx_step], this->residual_history_[idx_prev_step]);
121 this->scale(-1.0, this->output_history_[idx_prev_step]);
122 this->axpy(1.0, this->output_history_[idx_step], this->output_history_[idx_prev_step]);
125 for (
int i = 0; i <= history_size - 1; ++i) {
126 auto j = this->idx_hist(this->step_ - i - 1);
127 this->S_(history_size - 1, history_size - i - 1) = this->S_(history_size - i - 1, history_size - 1) = this->
template inner_product<normalize>(
128 this->residual_history_[j],
129 this->residual_history_[idx_prev_step]
134 for (
int i = 0; i < history_size; ++i)
135 for (
int j = 0; j < history_size; ++j)
136 this->S_factorized_(j, i) = this->S_(j, i);
139 for (
int i = 1; i <= history_size; ++i) {
140 auto j = this->idx_hist(this->step_ - i);
141 h(history_size - i) = this->
template inner_product<normalize>(
142 this->residual_history_[j],
143 this->residual_history_[idx_step]
151 for (
int i = 1; i <= history_size; ++i) {
152 auto j = this->idx_hist(this->step_ - i);
153 this->axpy(-this->beta_ * h(history_size - i), this->residual_history_[j], this->input_);
157 for (
int i = 1; i <= history_size; ++i) {
158 auto j = this->idx_hist(this->step_ - i);
159 this->axpy(-h(history_size - i), this->output_history_[j], this->input_);
162 this->history_size_ = 0;
167 if (this->history_size_ == this->max_history_ - 1) {
168 for (
int col = 0; col <= history_size - 2; ++col) {
169 for (
int row = 0; row <= history_size - 2; ++row) {
170 this->S_(row, col) = this->S_(row + 1, col + 1);
175 this->copy(this->input_, this->output_history_[idx_next_step]);
176 this->history_size_ = std::min(this->history_size_ + 1, this->max_history_ - 1);
Abstract mixer for variadic number of Function objects, which are described by FunctionProperties.
Linear algebra interface.
Memory management functions and classes.
Contains definition and implementation of sirius::Mixer base class.
Namespace of the SIRIUS library.