Flow123d  jenkins-Flow123d-windows-release-multijob-285
field_set.hh
Go to the documentation of this file.
1 /*
2  * field_set.hh
3  *
4  * Created on: Mar 8, 2014
5  * Author: jb
6  */
7 
8 #ifndef FIELD_SET_HH_
9 #define FIELD_SET_HH_
10 
11 
12 #include <system/exceptions.hh>
13 #include "fields/field.hh"
14 #include "fields/field_flag.hh"
15 
16 
17 
18 /**
19  * @brief Container for various descendants of FieldCommonBase.
20  *
21  * Provides various collective operations.
22  * Typical usage:
23  *
24  * class EqData : public FieldSet
25  * {
26  * EqData() {
27  * *this += scalar_field
28  * .name("scalar_field")
29  * .description("Some description for input and output documentation.")
30  * .input_default("{0.0}")
31  * .units("m");
32  * *this += vector_field
33  * .name("vector_field")
34  * .description("Some description for input and output documentation.")
35  * .units("m");
36  * }
37  *
38  * Field<3, FieldValue<3>::Scalar> scalar_field;
39  * Field<3, FieldValue<3>::Vector> vector_field;
40  * };
41  *
42  * This way the fields are destructed just before their pointers stored in the FieldSet.
43  *
44  * TODO:
45  * Some set_XY functions set also to the fields added to the FieldSet in future.
46  * This behavior should be removed, since it is misleading in combination with mask subsets. If one set
47  * something to mask subset, it does not influence fields added to the original field set even if
48  * they match the mask of the subset.
49  *
50  */
51 class FieldSet : public FieldFlag {
52 public:
53  DECLARE_EXCEPTION(ExcUnknownField, << "Field set has no field with name: " << FieldCommon::EI_Field::qval);
54 
55  /**
56  * Add an existing Field to the list. It stores just pointer to the field.
57  * Be careful to not destroy passed Field before the FieldSet.
58  *
59  * Using operator allows elegant setting and adding of a field to the field set:
60  * @code
61  * Field<...> init_quantity; // member of a FieldSet descendant
62  *
63  * field_set +=
64  * some_field
65  * .disable_where(type, {dirichlet, neumann}) // this must come first since it is not member of FieldCommonBase
66  * .name("init_temperature")
67  * .description("Initial temperature");
68  *
69  */
70  FieldSet &operator +=(FieldCommon &add_field);
71 
72  /**
73  * Add other FieldSet to current one.
74  */
75  FieldSet &operator +=(const FieldSet &other);
76 
77  /**
78  * Make new FieldSet as a subset of *this. The new FieldSet contains fields with names given by the @p names parameter.
79  */
80  FieldSet subset(std::vector<std::string> names) const;
81 
82  /**
83  * Make new FieldSet as a subset of *this.
84  * The new FieldSet contains all fields that match given @p mask.
85  */
86  FieldSet subset( FieldFlag::Flags::Mask mask) const;
87 
88  /**
89  * Number of fields in the FieldSet.
90  */
91  inline unsigned int size() const {
92  return field_list.size();
93  }
94 
95  /**
96  * Returns input type for a field descriptor, that can contain any of the fields in the set.
97  * Typical usage is from derived class, where we add fields in the constructor and make auxiliary temporary instance
98  * to get the record of the field descriptor. Simplest example:
99  *
100  * @code
101  * class EqData : public FieldSet {
102  * public:
103  * // fields
104  * Field<..> field_a;
105  * Field<..> field_b
106  * EqData() {
107  * add(field_a);
108  * add(field_b);
109  * }
110  * }
111  *
112  * Input::Type::Record SomEquation::input_type=
113  * Record("SomeEquation","equation's description")
114  * .declare_key("data",Input::Type::Array(EqData().make_field_descriptor_type()),"List of field descriptors.");
115  * @endcode
116  */
117  Input::Type::Record make_field_descriptor_type(const std::string &equation_name) const;
118 
119  /**
120  * Make Selection with strings for all field names in the FieldSet.
121  */
122  Input::Type::Selection make_output_field_selection(const string &name, const string &desc = "");
123 
124  /**
125  * Use @p FieldCommonBase::copy_from() to set field of the field set given by the first parameter
126  * @p dest_field_name. The source field is given as the second parameter @p source. The field
127  * copies share the same input descriptor list and the same instances of FieldBase classes
128  * but each copy can be set to different time and different limit side.
129  *
130  * See @p FieldCommonBase::copy_from documentation for details.
131  */
132  void set_field(const std::string &dest_field_name, FieldCommon &source);
133 
134  /**
135  * Return pointer to the field given by name @p field_name. Return nullptr if not found.
136  */
137  FieldCommon *field(const std::string &field_name) const;
138 
139  /**
140  * Returns reference to the field given by @p field_name.
141  * Throws if the field with given name is not found.
142  */
143  FieldCommon &operator[](const std::string &field_name) const;
144 
145  /**
146  * Collective interface to @p FieldCommonBase::set_components().
147  * It is safe to call this for field sets containing also fields
148  * with return value other then variable vector as long as all variable
149  * vector fields should be set to the same number of components.
150  */
151  void set_components(const std::vector<string> &names) {
152  for(auto field : field_list) field->set_components(names);
153  }
154  /**
155  * Collective interface to @p FieldCommonBase::set_mesh().
156  */
157  void set_mesh(const Mesh &mesh) {
158  for(auto field : field_list) field->set_mesh(mesh);
159  }
160 
161  /**
162  * Collective interface to @p FieldCommon::set_mesh().
163  */
164  void set_input_list(Input::Array input_list) {
165  for(auto field : field_list) field->set_input_list(input_list);
166  }
167 
168  /**
169  * Collective interface to @p FieldCommon::set_limit_side().
170  */
172  for(FieldCommon *field : field_list) field->set_limit_side(side);
173  }
174 
175  /**
176  * Collective interface to @p FieldCommonBase::flags_add().
177  * @param mask mask to set for all fields in the field set.
178  */
179  void flags_add( FieldFlag::Flags::Mask mask) {
180  for (auto field : field_list) field->flags_add(mask);
181  }
182 
183  /**
184  * Collective interface to @p FieldCommonBase::set_mesh().
185  */
186  void set_time(const TimeStep &time) {
187  for(auto field : field_list) field->set_time(time);
188  }
189 
190  /**
191  * Collective interface to @p FieldCommonBase::output_type().
192  * @param rt Discrete function space (element, node or corner data).
193  */
195  for (auto field : field_list) field->output_type(rt);
196  }
197 
198  /**
199  * Collective interface to @p FieldCommonBase::mar_input_times().
200  */
202  for(auto field : field_list) field->mark_input_times(mark_type);
203  }
204 
205  /**
206  * Collective interface to @p FieldCommonBase::set_mesh().
207  */
208  bool changed() const;
209 
210  /**
211  * Collective interface to @p FieldCommonBase::set_mesh().
212  */
213  bool is_constant(Region reg) const;
214 
215  /**
216  * Collective interface to @p FieldCommonBase::output().
217  */
218  void output(OutputTime *stream);
219 
220  /**
221  * OBSOLETE
222  *
223  * Adds given field into list of fields for group operations on fields.
224  * Parameters are: @p field pointer, @p name of the key in the input, @p desc - description of the key, and optional parameter
225  * @p d_val with default value. This method is rather called through the macro ADD_FIELD
226  */
227  FieldCommon &add_field( FieldCommon *field, const string &name,
228  const string &desc, const string & d_val="");
229 
230 protected:
231 
232 
233  /// List of all fields.
235 
236  /**
237  * Stream output operator
238  */
239  friend std::ostream &operator<<(std::ostream &stream, const FieldSet &set);
240 };
241 
242 
243 /**
244  * (OBSOLETE)
245  * Macro to simplify call of FieldSet::add_field method. Two forms are supported:
246  *
247  *
248  *
249  * ADD_FIELD(some_field, description);
250  * ADD_FIELD(some_field, description, Default);
251  *
252  * The first form adds name "some_field" to the field member some_field, also adds description of the field. No default
253  * value is specified, so the user must initialize the field on all regions (This is checked in the Field<..>::set_time method)
254  *
255  * The second form adds also default value to the field, that is Default(".."), or Default::read_time(), other default value specifications are
256  * meaningless. The automatic conversion to FieldConst is used, e.g. Default::("0.0") is automatically converted to
257  * { TYPE="FieldConst", value=[ 0.0 ] } for a vector valued field, so you get zero vector on output on regions with default value.
258  */
259 
260 #define ADD_FIELD(name, ...) this->add_field(&name, string(#name), __VA_ARGS__)
261 
262 
263 
264 
265 #endif /* FIELD_SET_HH_ */
void output_type(OutputTime::DiscreteSpace rt)
Definition: field_set.hh:194
std::vector< FieldCommon * > field_list
List of all fields.
Definition: field_set.hh:234
void set_input_list(Input::Array input_list)
Definition: field_set.hh:164
virtual void set_mesh(const Mesh &mesh)
void mark_input_times(TimeMark::Type mark_type)
void set_limit_side(LimitSide side)
Definition: field_set.hh:171
Common abstract parent of all Field<...> classes.
Definition: field_common.hh:47
Container for various descendants of FieldCommonBase.
Definition: field_set.hh:51
unsigned long int Type
Definition: time_marks.hh:64
void set_limit_side(LimitSide side)
FieldCommon & operator[](const std::string &field_name) const
Definition: field_set.cc:117
Accessor to input data conforming to declared Array.
Definition: accessors.hh:558
FieldCommon & flags_add(FieldFlag::Flags::Mask mask)
void set_time(const TimeStep &time)
Definition: field_set.hh:186
Definition: mesh.h:109
void set_input_list(const Input::Array &list)
Definition: field_common.cc:53
virtual bool set_time(const TimeStep &time)=0
FieldCommon * field(const std::string &field_name) const
Definition: field_set.cc:109
FieldCommon & add_field(FieldCommon *field, const string &name, const string &desc, const string &d_val="")
Definition: field_set.cc:153
void set_field(const std::string &dest_field_name, FieldCommon &source)
Definition: field_set.cc:101
void mark_input_times(TimeMark::Type mark_type)
Definition: field_set.hh:201
The class for outputting data during time.
Definition: output_time.hh:32
DECLARE_EXCEPTION(ExcUnknownField,<< "Field set has no field with name: "<< FieldCommon::EI_Field::qval)
void output(OutputTime *stream)
Definition: field_set.cc:143
void set_components(const std::vector< string > &names)
Definition: field_set.hh:151
bool is_constant(Region reg) const
Definition: field_set.cc:135
Input::Type::Selection make_output_field_selection(const string &name, const string &desc="")
Definition: field_set.cc:76
void set_mesh(const Mesh &mesh)
Definition: field_set.hh:157
friend std::ostream & operator<<(std::ostream &stream, const FieldSet &set)
Definition: field_set.cc:161
void set_components(const std::vector< string > &names)
Record type proxy class.
Definition: type_record.hh:169
Representation of one time step.
void flags_add(FieldFlag::Flags::Mask mask)
Definition: field_set.hh:179
bool changed() const
Definition: field_set.cc:127
Template for classes storing finite set of named values.
LimitSide
Definition: field_common.hh:33
FieldCommon & output_type(OutputTime::DiscreteSpace rt)
Input::Type::Record make_field_descriptor_type(const std::string &equation_name) const
Definition: field_set.cc:50