22#ifndef CCGSL_SIMAN_HPP
23#define CCGSL_SIMAN_HPP
27#include<gsl/gsl_machine.h>
28#include<gsl/gsl_siman.h>
59 typedef void (*
step_t)(
rng& r, XP& xp,
double step_size );
71 typedef void (*
copy_t)( XP& source, XP& dest );
75 typedef XP* (*copy_construct_t)( XP& xp );
110 double operator()(
double E,
double new_E,
double T,
params_t& params )
const {
111 double x = -(new_E -
E) / (params.k * T);
113 return (x < GSL_LOG_DBL_MIN) ? 0.0 :
std::exp(x);
118 void operator()( XP& src, XP& dst,
size_t size,
copy_t copyfunc )
const {
122 memcpy(
reinterpret_cast<void*
>( &dst ),
reinterpret_cast<void*
>( &src ),
size);
127 XP *x, *new_x, *best_x;
128 double E, new_E, best_E;
131 int n_evals = 1, n_iter = 0, n_accepts, n_rejects, n_eless;
136 size_t element_size = 0;
137 if( copyfunc == NULL ){
138 if( copy_constructor != NULL || destructor != NULL ){
139 std::cerr <<
"ccgsl::siman<XP>::solve(): "
140 <<
"this function requires that either the dynamic functions (copy, "
141 <<
"copy_constructor and destructor) are all passed, or that none are."
145 element_size =
sizeof( XP );
152 x = copy_constructor(x0_p);
153 new_x = copy_constructor(x0_p);
154 best_x = copy_constructor(x0_p);
156 x = (XP *) malloc (element_size);
157 memcpy (x,
reinterpret_cast<void*
>( &x0_p ), element_size);
159 new_x = (XP *) malloc (element_size);
160 best_x = (XP *) malloc (element_size);
161 memcpy (best_x,
reinterpret_cast<void*
>( &x0_p ), element_size);
166 T = params.t_initial;
167 T_factor = 1.0 / params.mu_t;
169 if (print_position) {
170 printf (
"#-iter #-evals temperature position energy\n");
179 for (i = 0; i < params.iters_fixed_T; ++i) {
181 copy_state(*x, *new_x, element_size, copyfunc);
183 take_step (r, *new_x, params.step_size);
188 copyfunc(*new_x,*best_x);
190 memcpy (best_x, new_x, element_size);
200 if (new_E < best_E) {
201 copy_state(*new_x, *best_x, element_size, copyfunc);
206 copy_state(*new_x, *x, element_size, copyfunc);
210 }
else if (r.
uniform() < boltzmann(
E, new_E, T, params)) {
212 copy_state(*new_x, *x, element_size, copyfunc);
221 if (print_position) {
226 printf (
"%5d %7d %12g", n_iter, n_evals, T);
228 printf (
" %12g %12g\n",
E, best_E);
235 if (T < params.t_min) {
242 copy_state(*best_x, x0_p, element_size, copyfunc);
274 double operator()(
double E,
double new_E,
double T,
params_t& params )
const {
275 double x = -(new_E -
E) / (params.k * T);
277 return (x < GSL_LOG_DBL_MIN) ? 0.0 :
std::exp(x);
281 size_t const element_size =
sizeof( XP );
285 double *energies, *probs, *sum_probs;
292 if (print_position) {
293 printf (
"#-iter temperature position");
294 printf (
" delta_pos energy\n");
297 x = (
void *) malloc (params.n_tries * element_size);
298 new_x = (
void *) malloc (params.n_tries * element_size);
299 energies = (
double *) malloc (params.n_tries * sizeof (
double));
300 probs = (
double *) malloc (params.n_tries * sizeof (
double));
301 sum_probs = (
double *) malloc (params.n_tries * sizeof (
double));
303 T = params.t_initial;
304 T_factor = 1.0 / params.mu_t;
306 memcpy (x, x0_p, element_size);
312 for (i = 0; i < params.n_tries - 1; ++i)
316 memcpy ((
char *)new_x + i * element_size, x, element_size);
317 take_step (r, (
char *)new_x + i * element_size, params.step_size);
318 energies[i] = Ef ((
char *)new_x + i * element_size);
319 probs[i] = boltzmann(Ex, energies[i], T, ¶ms);
322 memcpy ((
char *)new_x + (params.n_tries - 1) * element_size, x, element_size);
323 energies[params.n_tries - 1] = Ex;
324 probs[params.n_tries - 1] = boltzmann(Ex, energies[i], T, ¶ms);
327 sum_probs[0] = probs[0];
328 for (i = 1; i < params.n_tries; ++i)
330 sum_probs[i] = sum_probs[i - 1] + probs[i];
332 u = r.
uniform () * sum_probs[params.n_tries - 1];
333 for (i = 0; i < params.n_tries; ++i)
335 if (u < sum_probs[i])
337 memcpy (x, (
char *) new_x + i * element_size, element_size);
343 printf (
"%5d\t%12g\t", n_iter, T);
345 printf (
"\t%12g\t%12g\n", distance (x, x0_p), Ex);
349 if (T < params.t_min)
356 memcpy (x0_p, x, element_size);
double uniform() const
C++ version of gsl_rng_uniform().
size_t size(series const &cs)
C++ version of gsl_cheb_size().
complex exp(complex const &a)
C++ version of gsl_complex_exp().
The gsl package creates an interface to the GNU Scientific Library for C++.
static void solve(rng &r, XP &x0_p, Efunc_t Ef, step_t take_step, metric_t distance, print_t print_position, copy_t copyfunc, copy_construct_t copy_constructor, destroy_t destructor, params_t ¶ms)
C++ version of gsl_siman_solve().
void(* destroy_t)(XP *xp)
Function to destruct a configuration.
double(* Efunc_t)(XP &xp)
Function returning then energy of a configuration.
void(* print_t)(XP &xp)
Function to print a configuration.
void solve_many(rng &r, XP &x0_p, Efunc_t Ef, step_t take_step, metric_t distance, print_t print_position, params_t params)
C++ version of gsl_siman_solve_many().
XP *(* copy_construct_t)(XP &xp)
Function to construct a configuration.
void(* copy_t)(XP &source, XP &dest)
Function to copy configuration contents from source to dest.
gsl_siman_params_t params_t
Parameters: same as gsl_siman_params_t.
void(* step_t)(rng &r, XP &xp, double step_size)
Function to modify configuration with random number up to maximum step size.
double(* metric_t)(XP &xp, XP &yp)
Function to find distance between two configurations.