8 #ifndef FIELD_FORMULA_IMPL_HH_
9 #define FIELD_FORMULA_IMPL_HH_
15 #include <boost/foreach.hpp>
19 namespace it = Input::Type;
21 template <
int spacedim,
class Value>
24 template <
int spacedim,
class Value>
33 "String, array of strings, or matrix of strings with formulas for individual "
34 "entries of scalar, vector, or tensor value respectively.\n"
35 "For vector values, you can use just one string to enter homogeneous vector.\n"
36 "For square NxN-matrix values, you can use:\n"
37 "* array of strings of size N to enter diagonal matrix\n"
38 "* array of strings of size (N+1)*N/2 to enter symmetric matrix (upper triangle, row by row)\n"
39 "* just one string to enter (spatially variable) multiple of the unit matrix.\n"
40 "Formula can contain variables x,y,z,t and usual operators and functions." );
48 template <
int spacedim,
class Value>
51 formula_matrix_(this->value_.n_rows(), this->value_.n_cols()),
52 formula_matrix_helper_(formula_matrix_), parser_matrix_(this->value_.n_rows())
54 for(
unsigned int row=0; row < this->
value_.n_rows(); row++) {
61 template <
int spacedim,
class Value>
69 template <
int spacedim,
class Value>
73 bool any_parser_changed =
false;
76 std::string vars = string(
"x,y,z").substr(0, 2*spacedim-1);
78 for(
unsigned int row=0; row < this->value_.n_rows(); row++)
79 for(
unsigned int col=0; col < this->value_.n_cols(); col++) {
83 FunctionParser tmp_parser;
84 int err=tmp_parser.ParseAndDeduceVariables(formula_matrix_.at(row,col), var_list);
85 ASSERT( err != FunctionParser::FP_NO_ERROR,
"ParseAndDeduceVariables error: %s\n", tmp_parser.ErrorMsg() );
87 bool time_dependent =
false;
88 BOOST_FOREACH(std::string &var_name, var_list ) {
89 if (var_name == std::string(
"t") ) time_dependent=
true;
90 else if (var_name ==
"x" || var_name ==
"y" || var_name ==
"z")
continue;
92 xprintf(
Warn,
"Unknown variable '%s' in the FieldFormula[%d][%d] == '%s'\n at the input address:\n %s \n",
93 var_name.c_str(), row, col, formula_matrix_.at(row,col).c_str(),
94 value_input_address_.c_str() );
97 parser_matrix_[row][col].AddConstant(
"t", time);
104 if (time_dependent || this->time_ == -numeric_limits<double>::infinity() ) {
105 parser_matrix_[row][col].Parse(formula_matrix_.at(row,col), vars);
107 if ( parser_matrix_[row][col].GetParseErrorType() != FunctionParser::FP_NO_ERROR ) {
108 xprintf(
UsrErr,
"ParserError: %s\n in the FieldFormula[%d][%d] == '%s'\n at the input address:\n %s \n",
109 parser_matrix_[row][col].ErrorMsg(),
110 row,col,formula_matrix_.at(row,col).c_str(),
111 value_input_address_.c_str());
114 parser_matrix_[row][col].Optimize();
115 any_parser_changed =
true;
122 return any_parser_changed;
129 template <
int spacedim,
class Value>
132 for(
unsigned int row=0; row < this->value_.n_rows(); row++)
133 for(
unsigned int col=0; col < this->value_.n_cols(); col++) {
134 this->value_(row,col) = parser_matrix_[row][col].Eval(p.memptr());
136 return this->r_value_;
143 template <
int spacedim,
class Value>
148 for(
unsigned int i=0; i< point_list.size(); i++) {
149 Value envelope(value_list[i]);
151 for(
unsigned int row=0; row < this->value_.n_rows(); row++)
152 for(
unsigned int col=0; col < this->value_.n_cols(); col++) {
153 envelope(row,col) = parser_matrix_[row][col].Eval(point_list[i].memptr());
159 template <
int spacedim,
class Value>