Flow123d  JS_before_hm-1601-gc6ac32d
field_formula.hh
Go to the documentation of this file.
1 /*!
2  *
3  * Copyright (C) 2015 Technical University of Liberec. All rights reserved.
4  *
5  * This program is free software; you can redistribute it and/or modify it under
6  * the terms of the GNU General Public License version 3 as published by the
7  * Free Software Foundation. (http://www.gnu.org/licenses/gpl-3.0.en.html)
8  *
9  * This program is distributed in the hope that it will be useful, but WITHOUT
10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
11  * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
12  *
13  *
14  * @file field_formula.hh
15  * @brief
16  */
17 
18 #ifndef FIELD_FORMULA_HH_
19 #define FIELD_FORMULA_HH_
20 
21 
22 #define BOOST_MATH_DISABLE_FLOAT128
23 
24 
25 #include <stdio.h> // for sprintf
26 #include <string> // for operator==, string
27 #include <vector> // for vector
28 #include <memory>
29 #include <armadillo>
30 #include <map>
31 #include "fields/field_algo_base.hh" // for FieldAlgorithmBase
32 #include "fields/field_values.hh" // for FieldValue<>::Enum, FieldValu...
33 #include "fields/field_set.hh"
34 #include "input/accessors.hh" // for ExcAccessorForNullStorage
35 #include "input/accessors_impl.hh" // for Record::val
36 #include "input/storage.hh" // for ExcStorageTypeMismatch
37 #include "input/type_record.hh" // for Record::ExcRecordKeyNotFound
38 #include "input/input_exception.hh" // for ExcAssertMsg::~ExcAssertMsg
39 #include "system/exceptions.hh" // for ExcAssertMsg::~ExcAssertMsg
40 #include "tools/time_governor.hh" // for TimeStep
41 #include "include/assert.hh" // bparser
42 #include "include/parser.hh" // bparser
43 
44 class FunctionParser;
45 template <int spacedim> class ElementAccessor;
46 class SurfaceDepth;
47 
48 using namespace std;
49 
50 /**
51  * Class representing fields given by runtime parsed formulas.
52  *
53  * Using libraries:
54  * https://github.com/flow123d/bparser/
55  * http://warp.povusers.org/FunctionParser/ (gradually replaced by BParser)
56  *
57  * Allows parsing:
58  * - base variables: coordinates (x,y,z), time (t), surface depth (d); constants: e, pi
59  * - standard functions: trigonometric functions, min and max function, exponential function, ternary operator etc.
60  * - expressions dependendent on other fields
61  */
62 template <int spacedim, class Value>
63 class FieldFormula : public FieldAlgorithmBase<spacedim, Value>
64 {
65 public:
68 
69  TYPEDEF_ERR_INFO(EI_Field, std::string);
70  DECLARE_INPUT_EXCEPTION(ExcUnknownField,
71  << "Unknown field " << EI_Field::qval << " in the formula: \n");
72 
73  DECLARE_INPUT_EXCEPTION(ExcNotDoubleField,
74  << "Can not use integer valued field " << EI_Field::qval << " in the formula: \n");
75 
76  TYPEDEF_ERR_INFO(EI_BParserMsg, std::string);
77  DECLARE_INPUT_EXCEPTION(ExcParserError,
78  << "Parsing in " << EI_BParserMsg::val << " in the formula: \n");
79 
80  // Temporary exception of FParser. TODO remove at the same time as FParser
81  TYPEDEF_ERR_INFO(EI_FParserMsg, std::string);
82  TYPEDEF_ERR_INFO(EI_Row, unsigned int);
83  TYPEDEF_ERR_INFO(EI_Col, unsigned int);
84  TYPEDEF_ERR_INFO(EI_Formula, std::string);
85  DECLARE_INPUT_EXCEPTION(ExcFParserError,
86  << "ParserError: " << EI_FParserMsg::val << "\n in the FieldFormula[" << EI_Row::val
87  << "][" << EI_Row::val << "] == " << EI_Formula::qval << " \n");
88 
89  FieldFormula(unsigned int n_comp=0);
90 
91 
92  static const Input::Type::Record & get_input_type();
93 
94  virtual void init_from_input(const Input::Record &rec, const struct FieldAlgoBaseInitData& init_data);
95 
96  /**
97  * For time dependent formulas returns always true. For time independent formulas returns true only for the first time.
98  */
99  bool set_time(const TimeStep &time) override;
100 
101  /**
102  * Create SurfaceDepth object if surface region is set.
103  *
104  * See also description of the FieldBase<...>::set_mesh.
105  */
106  void set_mesh(const Mesh *mesh, bool boundary_domain) override;
107 
108  /**
109  * Returns one value in one given point. ResultType can be used to avoid some costly calculation if the result is trivial.
110  */
111  virtual typename Value::return_type const &value(const Point &p, const ElementAccessor<spacedim> &elm);
112 
113  /**
114  * Returns std::vector of scalar values in several points at once.
115  */
116  virtual void value_list (const Armor::array &point_list, const ElementAccessor<spacedim> &elm,
118 
119  void cache_update(FieldValueCache<typename Value::element_type> &data_cache,
120  ElementCacheMap &cache_map, unsigned int region_patch_idx) override;
121 
122  /**
123  * Set reference of FieldSet.
124  */
125  std::vector<const FieldCommon *> set_dependency(FieldSet &field_set) override;
126 
127  /**
128  * Overload @p FieldAlgorithmBase::cache_reinit
129  *
130  * Reinit arena data member.
131  */
132  void cache_reinit(const ElementCacheMap &cache_map) override;
133 
134  virtual ~FieldFormula();
135 
136 private:
138 
139  /**
140  * Evaluate depth variable if it is contained in formula.
141  *
142  * Return arma vec of point coordinates extended by depth value (or zero if depth is not contained.
143  */
144  inline arma::vec eval_depth_var(const Point &p);
145 
146  // StringValue::return_type == StringTensor, which behaves like arma::mat<string>
148 
149  // Matrix of parsers corresponding to the formula matrix returned by formula_matrix_helper_
152 
153  /// Accessor to Input::Record
155 
156  /// Surface depth object calculate distance from surface.
157  std::shared_ptr<SurfaceDepth> surface_depth_;
158 
159  /// Flag indicates if depth variable 'd' is used in formula - obsolete parameter of FParser
161 
162  /// Flag indicates if time variable 't' is used in formula - parameter of BParser
163  bool has_time_;
164 
165  /// Helper variable for construct of arena, holds sum of sizes (over shape) of all dependent fields.
167 
168  /// Flag indicates first call of set_time method, when FunctionParsers in parser_matrix_ must be initialized
170 
171  /// Arena object providing data arrays
172  bparser::ArenaAlloc * arena_alloc_;
173 
174  // BParser data arrays and variables
175  double *x_; ///< Coordinates x, part of previous array
176  double *y_; ///< Coordinates y, part of previous array
177  double *z_; ///< Coordinates z, part of previous array
178  double *d_; ///< Surface depth variable, used optionally if 'd' variable is set
179  double *res_; ///< Result vector of BParser
180  uint *subsets_; ///< Subsets indices in range 0 ... n-1
182 
183  /**
184  * Data of fields evaluated in expressions.
185  *
186  * Temporary data member, we need to copy data from FieldValueCaches to arrays allocated in arena.
187  */
188  std::unordered_map<const FieldCommon *, double *> eval_field_data_;
189 
190  /// Registrar of class to factory
191  static const int registrar;
192 
193 
194 };
195 
196 
197 #endif /* FIELD_FORMULA_HH_ */
double * y_
Coordinates y, part of previous array.
bool has_time_
Flag indicates if time variable &#39;t&#39; is used in formula - parameter of BParser.
double * z_
Coordinates z, part of previous array.
Container for various descendants of FieldCommonBase.
Definition: field_set.hh:159
ArmaVec< double, N > vec
Definition: armor.hh:885
unsigned int uint
bparser::ArenaAlloc * arena_alloc_
Arena object providing data arrays.
Directing class of FieldValueCache.
Definition: mesh.h:77
std::shared_ptr< SurfaceDepth > surface_depth_
Surface depth object calculate distance from surface.
Helper struct stores data for initizalize descentants of FieldAlgorithmBase.
StringTensorInput< Value::NRows_, Value::NCols_ > STI
FieldAlgorithmBase< spacedim, Value >::Point Point
bool first_time_set_
Flag indicates first call of set_time method, when FunctionParsers in parser_matrix_ must be initiali...
StringTensor formula_matrix_
Basic time management class.
static constexpr bool value
Definition: json.hpp:87
std::vector< const FieldCommon * > required_fields_
double * res_
Result vector of BParser.
bool has_depth_var_
Flag indicates if depth variable &#39;d&#39; is used in formula - obsolete parameter of FParser.
Accessor to the data with type Type::Record.
Definition: accessors.hh:291
uint * subsets_
Subsets indices in range 0 ... n-1.
#define TYPEDEF_ERR_INFO(EI_Type, Type)
Macro to simplify declaration of error_info types.
Definition: exceptions.hh:194
Space< spacedim >::Point Point
double * d_
Surface depth variable, used optionally if &#39;d&#39; variable is set.
#define DECLARE_INPUT_EXCEPTION(ExcName, Format)
Macro for simple definition of input exceptions.
static const int registrar
Registrar of class to factory.
Input::Record in_rec_
Accessor to Input::Record.
FieldAlgorithmBase< spacedim, Value > FactoryBaseType
std::vector< std::vector< FunctionParser > > parser_matrix_
Record type proxy class.
Definition: type_record.hh:182
double * x_
Coordinates x, part of previous array.
Representation of one time step..
std::vector< bparser::Parser > b_parser_
uint sum_shape_sizes_
Helper variable for construct of arena, holds sum of sizes (over shape) of all dependent fields...
std::unordered_map< const FieldCommon *, double * > eval_field_data_