Flow123d  release_2.2.0-41-g0958a8d
field_algo_base.impl.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_algo_base.impl.hh
15  * @brief
16  */
17 
18 #ifndef field_algo_base_IMPL_HH_
19 #define field_algo_base_IMPL_HH_
20 
21 #include <string>
22 #include <limits>
23 #include <memory>
24 using namespace std;
25 
28 #include "fields/field_python.hh"
29 #include "fields/field_constant.hh"
30 #include "fields/field_formula.hh"
32 
33 #include "fields/field_values.hh"
34 
35 #include "fields/unit_converter.hh"
36 
37 #include "tools/time_governor.hh"
38 #include "input/factory.hh"
39 #include "input/accessors.hh"
41 
42 namespace it = Input::Type;
43 
44 
45 
46 
47 /******************************************************************************************
48  * Implementation of FieldBase<...>
49  */
50 
51 template <int spacedim, class Value>
53 : value_(r_value_),
54  field_result_(result_other),
55  component_idx_(std::numeric_limits<unsigned int>::max()),
56  unit_conversion_coefficient_(1.0)
57 {
58  value_.set_n_comp(n_comp);
59 }
60 
61 
62 
63 template <int spacedim, class Value>
65  return boost::str(boost::format("R%i_to_%s") % spacedim % Value::type_name() );
66 }
67 
68 
69 
70 template <int spacedim, class Value>
72  stringstream ss;
73  ss << "[" << Value::NRows_ << ", " << Value::NCols_ << "]";
74  return it::Abstract("Field_"+template_name(), "Abstract for all time-space functions.")
75  .allow_auto_conversion("FieldConstant")
78  .close();
79 }
80 
81 
82 template <int spacedim, class Value>
85  if (is_enum_valued) {
86  ASSERT( !(value_selection==Input::Type::Selection()) ).error("Not defined 'value_selection' for enum element type.\n");
87  param_vec.push_back( std::make_pair("element_input_type", std::make_shared<it::Selection>(value_selection)) );
88  } else {
89  param_vec.push_back( std::make_pair("element_input_type", std::make_shared<typename Value::ElementInputType>()) );
90  }
91 
92  return it::Instance(get_input_type(), param_vec).close();
93 }
94 
95 template <int spacedim, class Value>
97  auto unit_record = it::Record("Unit",
98  "Specify unit of an input value. "
99  "Evaluation of the unit formula results into a coeficient and a "
100  "unit in terms of powers of base SI units. The unit must match "
101  "expected SI unit of the value, while the value provided on the input "
102  "is multiplied by the coefficient before further processing. "
103  "The unit formula have a form:\n"
104  "```\n"
105  "<UnitExpr>;<Variable>=<Number>*<UnitExpr>;...,\n"
106  "```\n"
107  "where ```<Variable>``` is a variable name and ```<UnitExpr>``` is a units expression "
108  "which consists of products and divisions of terms.\n\n"
109  "A term has a form: "
110  "```<Base>^<N>```, where ```<N>``` is an integer exponent and ```<Base>``` "
111  "is either a base SI unit, a derived unit, or a variable defined in the same unit formula. "
112  "Example, unit for the pressure head:\n\n"
113  "```MPa/rho/g_; rho = 990*kg*m^-3; g_ = 9.8*m*s^-2```"
114  )
115  .allow_auto_conversion("unit_formula")
116  .declare_key("unit_formula", it::String(), it::Default::obligatory(),
117  "Definition of unit." )
118  .close();
119 
120  return it::Record("FieldAlgorithmBase_common_aux", "")
121  .declare_key("unit", unit_record, it::Default::optional(),
122  "Unit of the field values provided in the main input file, in the external file, or "
123  "by a function (FieldPython).")
124  .close();
125 }
126 
127 template <int spacedim, class Value>
128 shared_ptr< FieldAlgorithmBase<spacedim, Value> >
130 {
131  shared_ptr< FieldAlgorithmBase<spacedim, Value> > func;
132  func = rec.factory< FieldAlgorithmBase<spacedim, Value> >(init_data.n_comp_);
133  func->init_from_input(rec, init_data);
134  return func;
135 }
136 
137 
138 
139 template <int spacedim, class Value>
141  xprintf(PrgErr, "The field '%s' do not support initialization from input.\n",
142  typeid(this).name());
143 }
144 
145 
146 
147 template <int spacedim, class Value>
149  time_ = time;
150  return false; // no change
151 }
152 
153 
154 
155 template <int spacedim, class Value>
156 void FieldAlgorithmBase<spacedim, Value>::set_mesh(const Mesh *mesh, bool boundary_domain) {
157 }
158 
159 
160 
161 template<int spacedim, class Value>
163  return (Value::NRows_ ? 0 : value_.n_rows());
164 }
165 
166 
167 
168 template<int spacedim, class Value>
170  const std::vector< Point > &point_list,
171  const ElementAccessor<spacedim> &elm,
173 {
174  ASSERT_EQ( point_list.size(), value_list.size() ).error();
175  for(unsigned int i=0; i< point_list.size(); i++) {
176  ASSERT( Value(value_list[i]).n_rows()==this->value_.n_rows() )(i)(Value(value_list[i]).n_rows())(this->value_.n_rows())
177  .error("value_list has wrong number of rows");
178  value_list[i]=this->value(point_list[i], elm);
179  }
180 
181 }
182 
183 template<int spacedim, class Value>
185  const struct FieldAlgoBaseInitData& init_data)
186 {
187  Input::Record unit_record;
188  if ( rec.opt_val("unit", unit_record) ) {
189  if (!Value::is_scalable()) {
190  WarningOut().fmt("Setting unit conversion coefficient of non-floating point field at address {}\nCoefficient will be skipped.\n",
191  rec.address_string());
192  }
193  std::string unit_str = unit_record.val<std::string>("unit_formula");
194  try {
195  this->unit_conversion_coefficient_ = init_data.unit_si_.convert_unit_from(unit_str);
196  } catch (ExcInvalidUnit &e) {
197  e << rec.ei_address();
198  throw;
199  } catch (ExcNoncorrespondingUnit &e) {
200  e << rec.ei_address();
201  throw;
202  }
203  }
204 }
205 
206 
207 
208 
209 #endif //FUNCTION_BASE_IMPL_HH_
TimeStep time_
Actual time level; initial value is -infinity.
void init_unit_conversion_coefficient(const Input::Record &rec, const struct FieldAlgoBaseInitData &init_data)
Init value of unit_conversion_coefficient_ from input.
Abstract & allow_auto_conversion(const string &type_default)
Allows shorter input of the Abstract providing the default value to the "TYPE" key.
static const Input::Type::Instance & get_input_type_instance(Input::Type::Selection value_selection=Input::Type::Selection())
virtual bool set_time(const TimeStep &time)
double convert_unit_from(std::string actual_unit) const
Convert and check user-defined unit.
Definition: unit_si.cc:217
const Instance & close() const
Used for set Instance to TypeRepository.
virtual void value_list(const std::vector< Point > &point_list, const ElementAccessor< spacedim > &elm, std::vector< typename Value::return_type > &value_list)=0
std::string format(CStringRef format_str, ArgList args)
Definition: format.h:3141
static Default obligatory()
The factory function to make an empty default value which is obligatory.
Definition: type_record.hh:110
Definition: mesh.h:97
Helper class that stores data of generic types.
Definition: type_generic.hh:89
Helper struct stores data for initizalize descentants of FieldAlgorithmBase.
#define ASSERT(expr)
Allow use shorter versions of macro names if these names is not used with external library...
Definition: asserts.hh:346
virtual Value::return_type const & value(const Point &p, const ElementAccessor< spacedim > &elm)=0
Abstract & add_attribute(std::string key, TypeBase::json_string value)
Frontend to TypeBase::add_attribute_.
Record & close() const
Close the Record for further declarations of keys.
Definition: type_record.cc:303
Basic time management class.
static constexpr bool is_enum_valued
double unit_conversion_coefficient_
Coeficient of conversion of user-defined unit.
EI_Address ei_address() const
Definition: accessors.cc:178
static Default optional()
The factory function to make an empty default value which is optional.
Definition: type_record.hh:124
bool opt_val(const string &key, Ret &value) const
virtual Record & allow_auto_conversion(const string &from_key)
Allows shorter input of the Record providing only value of the from_key given as the parameter...
Definition: type_record.cc:132
virtual void init_from_input(const Input::Record &rec, const struct FieldAlgoBaseInitData &init_data)
Accessor to the data with type Type::Record.
Definition: accessors.hh:292
const Ret val(const string &key) const
#define xprintf(...)
Definition: system.hh:92
static string field_value_shape()
Record & declare_key(const string &key, std::shared_ptr< TypeBase > type, const Default &default_value, const string &description, TypeBase::attribute_map key_attributes=TypeBase::attribute_map())
Declares a new key of the Record.
Definition: type_record.cc:490
Class for declaration of polymorphic Record.
Accessor to the polymorphic input data of a type given by an AbstracRecord object.
Definition: accessors.hh:459
Abstract & root_of_generic_subtree()
static std::shared_ptr< FieldAlgorithmBase< spacedim, Value > > function_factory(const Input::AbstractRecord &rec, const struct FieldAlgoBaseInitData &init_data)
const UnitSI & unit_si_
FieldAlgorithmBase(unsigned int n_comp=0)
Value value_
Last value, prevents passing large values (vectors) by value.
Definition: system.hh:64
static Input::Type::Abstract & get_input_type()
virtual void set_mesh(const Mesh *mesh, bool boundary_domain)
#define WarningOut()
Macro defining &#39;warning&#39; record of log.
Definition: logger.hh:236
Record type proxy class.
Definition: type_record.hh:182
const std::shared_ptr< Type > factory(Arguments...arguments) const
static const Input::Type::Record & get_field_algo_common_keys()
static std::string template_name()
Class for declaration of the input data that are in string format.
Definition: type_base.hh:588
Representation of one time step..
Template for classes storing finite set of named values.
#define ASSERT_EQ(a, b)
Definition of comparative assert macro (EQual)
Definition: asserts.hh:327
unsigned int n_comp() const
string address_string() const
Definition: accessors.cc:184