version 1.14 | version 1.15 |
---|
| |
/// -*- c++ -*- | // -*- c++ -*- |
| |
#ifndef COLVARGRID_H | #ifndef COLVARGRID_H |
#define COLVARGRID_H | #define COLVARGRID_H |
| |
return mult; | return mult; |
} | } |
| |
| /// \brief Request grid to use actual values of extended coords |
| inline void request_actual_value(bool b = true) |
| { |
| size_t i; |
| for (i = 0; i < actual_value.size(); i++) { |
| actual_value[i] = b; |
| } |
| } |
| |
/// \brief Allocate data | /// \brief Allocate data |
int setup(std::vector<int> const &nx_i, | int setup(std::vector<int> const &nx_i, |
T const &t = T(), | T const &t = T(), |
| |
| |
size_t i; | size_t i; |
| |
for (i = 0; i < cv.size(); i++) { | |
if (!cv[i]->tasks[colvar::task_lower_boundary] || | |
!cv[i]->tasks[colvar::task_upper_boundary]) { | |
cvm::error("Tried to initialize a grid on a " | |
"variable with undefined boundaries.\n", INPUT_ERROR); | |
return COLVARS_ERROR; | |
} | |
} | |
| |
if (cvm::debug()) { | if (cvm::debug()) { |
cvm::log("Allocating a grid for "+cvm::to_str(colvars.size())+ | cvm::log("Allocating a grid for "+cvm::to_str(colvars.size())+ |
" collective variables, multiplicity = "+cvm::to_str(mult_i)+".\n"); | " collective variables, multiplicity = "+cvm::to_str(mult_i)+".\n"); |
| |
| |
// except if a colvar is specified twice in a row | // except if a colvar is specified twice in a row |
// then the first instance is the actual value | // then the first instance is the actual value |
| // For histograms of extended-system coordinates |
if (i > 0 && cv[i-1] == cv[i]) { | if (i > 0 && cv[i-1] == cv[i]) { |
actual_value[i-1] = true; | actual_value[i-1] = true; |
} | } |
| |
return value_to_bin_scalar(actual_value[i] ? cv[i]->actual_value() : cv[i]->value(), i); | return value_to_bin_scalar(actual_value[i] ? cv[i]->actual_value() : cv[i]->value(), i); |
} | } |
| |
| /// \brief Report the bin corresponding to the current value of item iv in variable i |
| inline int current_bin_scalar(int const i, int const iv) const |
| { |
| return value_to_bin_scalar(actual_value[i] ? |
| cv[i]->actual_value().vector1d_value[iv] : |
| cv[i]->value().vector1d_value[iv], i); |
| } |
| |
/// \brief Use the lower boundary and the width to report which bin | /// \brief Use the lower boundary and the width to report which bin |
/// the provided value is in | /// the provided value is in |
inline int value_to_bin_scalar(colvarvalue const &value, const int i) const | inline int value_to_bin_scalar(colvarvalue const &value, const int i) const |
| |
} | } |
| |
/// Read a grid definition from a config string | /// Read a grid definition from a config string |
int parse_params(std::string const &conf) | int parse_params(std::string const &conf, |
| colvarparse::Parse_Mode const parse_mode = colvarparse::parse_normal) |
{ | { |
if (cvm::debug()) cvm::log("Reading grid configuration from string.\n"); | if (cvm::debug()) cvm::log("Reading grid configuration from string.\n"); |
| |
| |
| |
{ | { |
size_t nd_in = 0; | size_t nd_in = 0; |
| // this is only used in state files |
colvarparse::get_keyval(conf, "n_colvars", nd_in, nd, colvarparse::parse_silent); | colvarparse::get_keyval(conf, "n_colvars", nd_in, nd, colvarparse::parse_silent); |
if (nd_in != nd) { | if (nd_in != nd) { |
cvm::error("Error: trying to read data for a grid " | cvm::error("Error: trying to read data for a grid " |
| |
} | } |
} | } |
| |
| // underscore keywords are used in state file |
colvarparse::get_keyval(conf, "lower_boundaries", | colvarparse::get_keyval(conf, "lower_boundaries", |
lower_boundaries, lower_boundaries, colvarparse::parse_silent); | lower_boundaries, lower_boundaries, colvarparse::parse_silent); |
colvarparse::get_keyval(conf, "upper_boundaries", | colvarparse::get_keyval(conf, "upper_boundaries", |
upper_boundaries, upper_boundaries, colvarparse::parse_silent); | upper_boundaries, upper_boundaries, colvarparse::parse_silent); |
| |
// support also camel case | // camel case keywords are used in config file |
colvarparse::get_keyval(conf, "lowerBoundaries", | colvarparse::get_keyval(conf, "lowerBoundaries", |
lower_boundaries, lower_boundaries, colvarparse::parse_silent); | lower_boundaries, lower_boundaries, parse_mode); |
colvarparse::get_keyval(conf, "upperBoundaries", | colvarparse::get_keyval(conf, "upperBoundaries", |
upper_boundaries, upper_boundaries, colvarparse::parse_silent); | upper_boundaries, upper_boundaries, parse_mode); |
| |
colvarparse::get_keyval(conf, "widths", widths, widths, colvarparse::parse_silent); | colvarparse::get_keyval(conf, "widths", widths, widths, parse_mode); |
| |
| // only used in state file |
colvarparse::get_keyval(conf, "sizes", nx, nx, colvarparse::parse_silent); | colvarparse::get_keyval(conf, "sizes", nx, nx, colvarparse::parse_silent); |
| |
if (nd < lower_boundaries.size()) nd = lower_boundaries.size(); | if (nd < lower_boundaries.size()) nd = lower_boundaries.size(); |
| |
if ((is >> key) && (key == std::string("grid_parameters"))) { | if ((is >> key) && (key == std::string("grid_parameters"))) { |
is.seekg(start_pos, std::ios::beg); | is.seekg(start_pos, std::ios::beg); |
is >> colvarparse::read_block("grid_parameters", conf); | is >> colvarparse::read_block("grid_parameters", conf); |
parse_params(conf); | parse_params(conf, colvarparse::parse_silent); |
} else { | } else { |
cvm::log("Grid parameters are missing in the restart file, using those from the configuration.\n"); | cvm::log("Grid parameters are missing in the restart file, using those from the configuration.\n"); |
is.seekg(start_pos, std::ios::beg); | is.seekg(start_pos, std::ios::beg); |
| |
| |
/// \brief Write the grid data without labels, as they are | /// \brief Write the grid data without labels, as they are |
/// represented in memory | /// represented in memory |
/// \param buf_size Number of values per line | |
std::ostream & write_opendx(std::ostream &os) | std::ostream & write_opendx(std::ostream &os) |
{ | { |
// write the header | // write the header |
| |
} | } |
has_data = true; | has_data = true; |
} | } |
| |
| /// \brief Return the log-gradient from finite differences |
| /// on the *same* grid for dimension n |
| inline const cvm::real log_gradient_finite_diff( const std::vector<int> &ix0, |
| int n = 0) |
| { |
| cvm::real A0, A1; |
| std::vector<int> ix; |
| |
| // factor for mesh width, 2.0 for central finite difference |
| // but only 1.0 on edges for non-PBC coordinates |
| cvm::real factor; |
| |
| if (periodic[n]) { |
| factor = 2.; |
| ix = ix0; |
| ix[n]--; wrap(ix); |
| A0 = data[address(ix)]; |
| ix = ix0; |
| ix[n]++; wrap(ix); |
| A1 = data[address(ix)]; |
| } else { |
| factor = 0.; |
| ix = ix0; |
| if (ix[n] > 0) { // not left edge |
| ix[n]--; |
| factor += 1.; |
| } |
| A0 = data[address(ix)]; |
| ix = ix0; |
| if (ix[n]+1 < nx[n]) { // not right edge |
| ix[n]++; |
| factor += 1.; |
| } |
| A1 = data[address(ix)]; |
| } |
| if (A0 == 0 || A1 == 0) { |
| // can't handle empty bins |
| return 0.; |
| } else { |
| return (std::log((cvm::real)A1) - std::log((cvm::real)A0)) |
| / (widths[n] * factor); |
| } |
| } |
}; | }; |
| |
| |