Flow123d  release_2.2.1-10-gb9fad4d
field.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.impl.hh
15  * @brief
16  */
17 
18 #ifndef FIELD_IMPL_HH_
19 #define FIELD_IMPL_HH_
20 
21 #include <boost/foreach.hpp>
22 
23 #include "field.hh"
24 #include "field_algo_base.impl.hh"
25 #include "mesh/region.hh"
27 #include "input/accessors.hh"
28 #include "io/observe.hh"
29 #include "io/output_mesh.hh"
30 #include "io/output_element.hh"
31 
32 
33 /******************************************************************************************
34  * Implementation of Field<...>
35  */
36 
37 template<int spacedim, class Value>
39 : data_(std::make_shared<SharedData>())
40 {
41  // n_comp is nonzero only for variable size vectors Vector, VectorEnum, ..
42  // this invariant is kept also by n_comp setter
43  shared_->n_comp_ = (Value::NRows_ ? 0 : 1);
44  this->add_factory( std::make_shared<FactoryBase>() );
45 
46  this->multifield_ = false;
47 }
48 
49 
50 template<int spacedim, class Value>
51 Field<spacedim,Value>::Field(const string &name, bool bc)
52 : data_(std::make_shared<SharedData>())
53 
54 {
55  // n_comp is nonzero only for variable size vectors Vector, VectorEnum, ..
56  // this invariant is kept also by n_comp setter
57  shared_->n_comp_ = (Value::NRows_ ? 0 : 1);
58  shared_->bc_=bc;
59  this->name( name );
60  this->add_factory( std::make_shared<FactoryBase>() );
61  this->multifield_ = false;
62 }
63 
64 
65 
66 template<int spacedim, class Value>
67 Field<spacedim,Value>::Field(unsigned int component_index, string input_name, string name, bool bc)
68 : data_(std::make_shared<SharedData>())
69 {
70  // n_comp is nonzero only for variable size vectors Vector, VectorEnum, ..
71  // this invariant is kept also by n_comp setter
72  shared_->n_comp_ = (Value::NRows_ ? 0 : 1);
73  this->set_component_index(component_index);
74  this->name_ = (name=="") ? input_name : name;
75  this->shared_->input_name_ = input_name;
76  shared_->bc_ = bc;
77 
78  this->multifield_ = false;
79 }
80 
81 
82 template<int spacedim, class Value>
84 : FieldCommon(other),
85  data_(other.data_),
87  factories_(other.factories_)
88 {
89  if (other.no_check_control_field_)
90  no_check_control_field_ = make_shared<ControlField>(*other.no_check_control_field_);
91 
92  this->multifield_ = false;
93 }
94 
95 
96 template<int spacedim, class Value>
98 {
99  //OLD_ASSERT( flags().match( FieldFlag::input_copy ) , "Try to assign to non-copy field '%s' from the field '%s'.", this->name().c_str(), other.name().c_str());
100  OLD_ASSERT(other.shared_->mesh_, "Must call set_mesh before assign to other field.\n");
101  OLD_ASSERT( !shared_->mesh_ || (shared_->mesh_==other.shared_->mesh_),
102  "Assignment between fields with different meshes.\n");
103 
104  // check for self assignement
105  if (&other == this) return *this;
106 
107  // class members derived from FieldCommon
108  shared_ = other.shared_;
109  shared_->is_fully_initialized_ = false;
111  last_time_ = other.last_time_;
115  this->multifield_ = false;
116 
117  // class members of Field class
118  data_ = other.data_;
119  factories_ = other.factories_;
121 
122  if (other.no_check_control_field_) {
123  no_check_control_field_ = make_shared<ControlField>(*other.no_check_control_field_);
124  }
125 
126  return *this;
127 }
128 
129 
130 
131 template<int spacedim, class Value>
133  return FieldBaseType::get_input_type_instance(shared_->input_element_selection_);
134 }
135 
136 
137 
138 template<int spacedim, class Value>
140  OLD_ASSERT(false, "This method can't be used for Field");
141 
142  it::Array arr = it::Array( it::Integer() );
143  return arr;
144 }
145 
146 
147 
148 template<int spacedim, class Value>
150  const Field<spacedim, typename FieldValue<spacedim>::Enum > &control_field,
151  const vector<FieldEnum> &value_list) -> Field &
152 {
153  no_check_control_field_=std::make_shared<ControlField>(control_field);
154  shared_->no_check_values_=value_list;
155  return *this;
156 }
157 
158 template<int spacedim, class Value>
159 void Field<spacedim,Value>::set_mesh(const Mesh &in_mesh) {
160  // since we allow copy of fields before set_mesh is called
161  // we have to check that all copies set the same mesh
162  if (shared_->mesh_ && shared_->mesh_ != &in_mesh) {
163  THROW(ExcFieldMeshDifference() << EI_Field(name()) );
164  }
165 
166  shared_->mesh_ = &in_mesh;
167 
168  // initialize table if it is empty, we assume that the RegionDB is closed at this moment
169  region_fields_.resize( mesh()->region_db().size() );
170  RegionHistory init_history(history_length_limit_); // capacity
171  data_->region_history_.resize( mesh()->region_db().size(), init_history );
172 
173  if (no_check_control_field_) no_check_control_field_->set_mesh(in_mesh);
174 }
175 
176 
177 /*
178 template<int spacedim, class Value>
179 std::shared_ptr< typename Field<spacedim,Value>::FieldBaseType >
180 Field<spacedim,Value>::operator[] (Region reg)
181 {
182  OLD_ASSERT_LESS(reg.idx(), this->region_fields_.size());
183  return this->region_fields_[reg.idx()];
184 }
185 */
186 
187 
188 template <int spacedim, class Value>
190  OLD_ASSERT(this->set_time_result_ != TimeStatus::unknown, "Unknown time status.\n");
191  OLD_ASSERT_LESS(reg.idx(), this->region_fields_.size());
192  FieldBasePtr region_field = this->region_fields_[reg.idx()];
193  return (region_field && typeid(*region_field) == typeid(FieldConstant<spacedim, Value>));
194 }
195 
196 
197 template<int spacedim, class Value>
199  const RegionSet &domain,
200  FieldBasePtr field,
201  double time)
202 {
203  OLD_ASSERT(field, "Null field pointer.\n");
204 
205  OLD_ASSERT( mesh(), "Null mesh pointer, set_mesh() has to be called before set_field().\n");
206  if (domain.size() == 0) return;
207 
208  OLD_ASSERT_EQUAL( field->n_comp() , n_comp());
209  field->set_mesh( mesh() , is_bc() );
210 
211  HistoryPoint hp = HistoryPoint(time, field);
212  for(const Region &reg: domain) {
213  RegionHistory &region_history = data_->region_history_[reg.idx()];
214  // insert hp into descending time sequence
215  OLD_ASSERT( region_history.size() == 0 || region_history[0].first < hp.first, "Can not insert smaller time %g then last time %g in field's history.\n",
216  hp.first, region_history[0].first );
217  region_history.push_front(hp);
218  }
220 }
221 
222 
223 
224 template<int spacedim, class Value>
226  const RegionSet &domain,
227  const Input::AbstractRecord &a_rec,
228  double time)
229 {
230  FieldAlgoBaseInitData init_data(input_name(), n_comp(), units(), limits());
231  set_field(domain, FieldBaseType::function_factory(a_rec, init_data), time);
232 }
233 
234 
235 
236 
237 template<int spacedim, class Value>
238 bool Field<spacedim, Value>::set_time(const TimeStep &time_step, LimitSide limit_side)
239 {
240  OLD_ASSERT( mesh() , "NULL mesh pointer of field '%s'. set_mesh must be called before.\n",name().c_str());
241 
242  // Skip setting time if the new time is equal to current time of the field
243  // and if either the field is continuous in that time or the current limit side is same as the new one.
244  if (time_step.end() == last_time_) {
245  if ( ! is_jump_time() ||
246  limit_side == last_limit_side_) {
247  last_limit_side_ = limit_side;
248  return changed();
249  }
250  }
251 
252  last_time_=time_step.end();
253  last_limit_side_ = limit_side;
254 
255  // possibly update our control field
257  no_check_control_field_->set_time(time_step, limit_side);
258  }
259 
261 
262  // read all descriptors satisfying time.ge(input_time)
263  update_history(time_step);
265 
266  //
267  is_jump_time_=false;
268  // set time_step on all regions
269  // for regions that match type of the field domain
270  for(const Region &reg: mesh()->region_db().get_region_set("ALL") ) {
271  auto rh = data_->region_history_[reg.idx()];
272 
273  // skip regions with no matching BC flag
274  if (reg.is_boundary() != is_bc()) continue;
275 
276  // Check regions with empty history, possibly set default.
277  if ( rh.empty()) continue;
278 
279  double last_time_in_history = rh.front().first;
280  unsigned int history_size=rh.size();
281  unsigned int i_history;
282  OLD_ASSERT(time_step.ge(last_time_in_history), "Setting field time back in history not fully supported yet!");
283 
284  // set history index
285  if ( time_step.gt(last_time_in_history) ) {
286  // in smooth time_step
287  i_history=0;
288  } else {
289  // time_step .eq. input_time; i.e. jump time
290  is_jump_time_=true;
291  if (limit_side == LimitSide::right) {
292  i_history=0;
293  } else {
294  i_history=1;
295  }
296  }
297  i_history=min(i_history, history_size - 1);
298  OLD_ASSERT(i_history >= 0, "Empty field history.");
299  // possibly update field pointer
300 
301  auto new_ptr = rh.at(i_history).second;
302  if (new_ptr != region_fields_[reg.idx()]) {
303  region_fields_[reg.idx()]=new_ptr;
305  }
306  // let FieldBase implementation set the time
307  if ( new_ptr->set_time(time_step) ) set_time_result_ = TimeStatus::changed;
308 
309  }
310 
311  return changed();
312 }
313 
314 
315 template<int spacedim, class Value>
317  ASSERT( flags().match(FieldFlag::equation_input))(other.name().c_str())(this->name().c_str())
318  .error("Can not copy to the non-input field.");
319 
320  // do not use copy if the field have its own input
322  && this->shared_->input_list_.size() != 0 ) return;
323 
324  if (typeid(other) == typeid(*this)) {
325  auto const &other_field = dynamic_cast< Field<spacedim, Value> const &>(other);
326  this->operator=(other_field);
327  }
328 }
329 
330 
331 
332 template<int spacedim, class Value>
333 void Field<spacedim, Value>::field_output(std::shared_ptr<OutputTime> stream)
334 {
335  // currently we cannot output boundary fields
336  if (!is_bc()) {
337  const OutputTime::DiscreteSpace type = this->output_type();
338 
340 
342  for(unsigned int ids=0; ids < OutputTime::N_DISCRETE_SPACES; ids++)
343  if (flags & (1 << ids))
344  this->compute_field_data( OutputTime::DiscreteSpace(ids), stream);
345  }
346 }
347 
348 
349 template<int spacedim, class Value>
350 void Field<spacedim, Value>::observe_output(std::shared_ptr<Observe> observe)
351 {
352  typedef typename Value::element_type ElemType;
353 
354  if (observe->points().size() == 0) return;
355 
356  ElementDataCache<ElemType> &output_data = observe->prepare_compute_data<ElemType>(this->name(), this->time(),
357  (unsigned int)Value::NRows_, (unsigned int)Value::NCols_);
358 
359  unsigned int i_data=0;
360  for(const ObservePoint &o_point : observe->points()) {
361  unsigned int ele_index = o_point.element_idx();
362  const Value &obs_value =
363  Value( const_cast<typename Value::return_type &>(
364  this->value(o_point.global_coords(),
365  ElementAccessor<spacedim>(this->mesh(), ele_index, false)) ));
366  ASSERT_EQ(output_data.n_elem(), obs_value.n_rows()*obs_value.n_cols()).error();
367  output_data.store_value(i_data, obs_value.mem_ptr());
368  i_data++;
369  }
370 }
371 
372 
373 
374 template<int spacedim, class Value>
376 
377  FieldResult result_all = result_none;
378  for(Region &reg : region_set) {
379  auto f = region_fields_[reg.idx()];
380  if (f) {
381  FieldResult fr = f->field_result();
382  if (result_all == result_none) // first region
383  result_all = fr;
384  else if (fr != result_all)
385  result_all = result_other; // if results from individual regions are different
386  } else return result_none; // if field is undefined on any region of the region set
387  }
388 
389  if (result_all == result_constant && region_set.size() > 1)
390  return result_other; // constant result for individual regions could be non-constant on the whole region set
391 
392  return result_all;
393 
394 }
395 
396 
397 template<int spacedim, class Value>
399 {
400  int nrows = Value::NRows_;
401  int ncols = Value::NCols_;
402  string type = "Integer";
404  type = "Double";
405 
406  return fmt::format("{{ \"shape\": [ {}, {} ], \"type\": \"{}\", \"limit\": [ {}, {} ] }}",
407  nrows, ncols, type, this->limits().first, this->limits().second);
408 }
409 
410 
411 template<int spacedim, class Value>
413  OLD_ASSERT( mesh(), "Null mesh pointer, set_mesh() has to be called before.\n");
414 
415  // read input up to given time
416  double input_time;
417  if (shared_->input_list_.size() != 0) {
418  while( shared_->list_idx_ < shared_->input_list_.size()
419  && time.ge( input_time = shared_->input_list_[shared_->list_idx_].val<double>("time") ) ) {
420 
421  const Input::Record & actual_list_item = shared_->input_list_[shared_->list_idx_];
422  // get domain specification
423  RegionSet domain;
424  Input::Array domain_name_array;
425  unsigned int id;
426  if (actual_list_item.opt_val("region", domain_name_array)) {
427  std::vector<string> domain_names = mesh()->region_db().get_and_check_operands(domain_name_array);
428  domain = mesh()->region_db().union_set(domain_names);
429 
430  } else if (actual_list_item.opt_val("rid", id)) {
431  Region region;
432  try {
433  region = mesh()->region_db().find_id(id);
434  } catch (RegionDB::ExcUniqueRegionId &e) {
435  e << actual_list_item.ei_address();
436  throw;
437  }
438  if (region.is_valid())
439  domain.push_back(region);
440  else
441  THROW(RegionDB::ExcUnknownRegion() << RegionDB::EI_ID(id) );
442  } else {
443  THROW(ExcMissingDomain()
444  << actual_list_item.ei_address() );
445  }
446 
447  // get field instance
448  for(auto rit = factories_.rbegin() ; rit != factories_.rend(); ++rit) {
449  FieldBasePtr field_instance = (*rit)->create_field(actual_list_item, *this);
450  if (field_instance) // skip descriptors without related keys
451  {
452  // add to history
453  OLD_ASSERT_EQUAL( field_instance->n_comp() , n_comp());
454  field_instance->set_mesh( mesh() , is_bc() );
455  for(const Region &reg: domain) {
456  // if region history is empty, add new field
457  // or if region history is not empty and the input_time is higher, add new field
458  // otherwise (region history is not empty and the input_time is the same),
459  // rewrite the region field
460  if( data_->region_history_[reg.idx()].size() == 0
461  || data_->region_history_[reg.idx()].back().first < input_time)
462  {
463  data_->region_history_[reg.idx()].push_front(
464  HistoryPoint(input_time, field_instance));
465  //DebugOut() << "Update history" << print_var(this->name()) << print_var(reg.label()) << print_var(input_time);
466  }
467  else
468  {
469  data_->region_history_[reg.idx()].back() =
470  HistoryPoint(input_time, field_instance);
471  }
472  }
473  break;
474  }
475  }
476 
477  ++shared_->list_idx_;
478  }
479  }
480 }
481 
482 template<int spacedim, class Value>
484  OLD_ASSERT(mesh(), "Null mesh pointer.");
485  //if (shared_->is_fully_initialized_) return;
486 
487  // check there are no empty field pointers, collect regions to be initialized from default value
488  RegionSet regions_to_init; // empty vector
489 
490  for(const Region &reg : mesh()->region_db().get_region_set("ALL") )
491  if (reg.is_boundary() == is_bc()) { // for regions that match type of the field domain
492  RegionHistory &rh = data_->region_history_[reg.idx()];
493  if ( rh.empty() || ! rh[0].second) // empty region history
494  {
495  // test if check is turned on and control field is FieldConst
496  if (no_check_control_field_ && no_check_control_field_->is_constant(reg) ) {
497  // get constant enum value
498  auto elm = ElementAccessor<spacedim>(mesh(), reg);
499  FieldEnum value = no_check_control_field_->value(elm.centre(),elm);
500  // check that the value is in the disable list
501  if ( std::find(shared_->no_check_values_.begin(), shared_->no_check_values_.end(), value)
502  != shared_->no_check_values_.end() )
503  continue; // the field is not needed on this region
504  }
505  if (shared_->input_default_ != "") { // try to use default
506  regions_to_init.push_back( reg );
507  } else {
508  xprintf(UsrErr, "Missing value of the input field '%s' ('%s') on region ID: %d label: %s.\n",
509  input_name().c_str(), name().c_str(), reg.id(), reg.label().c_str() );
510  }
511  }
512  }
513 
514  // possibly set from default value
515  if ( regions_to_init.size() ) {
516  std::string region_list;
517  // has to deal with fact that reader can not deal with input consisting of simple values
518  string default_input=input_default();
519  auto input_type = get_input_type().make_instance().first;
520  Input::ReaderToStorage reader( default_input, *input_type, Input::FileFormat::format_JSON );
521 
522  auto a_rec = reader.get_root_interface<Input::AbstractRecord>();
523  FieldAlgoBaseInitData init_data(input_name(), n_comp(), units(), limits());
524  auto field_ptr = FieldBaseType::function_factory( a_rec , init_data );
525  field_ptr->set_mesh( mesh(), is_bc() );
526  for(const Region &reg: regions_to_init) {
527  data_->region_history_[reg.idx()]
528  .push_front(HistoryPoint( 0.0, field_ptr) );
529  region_list+=" "+reg.label();
530  }
531  FieldCommon::messages_data_.push_back( MessageData(input_default(), name(), region_list) );
532 
533  }
534  //shared_->is_fully_initialized_ = true;
535 }
536 
537 
538 template<int spacedim, class Value>
539 void Field<spacedim,Value>::add_factory(const std::shared_ptr<FactoryBase> factory) {
540  factories_.push_back( factory );
541 }
542 
543 
544 template<int spacedim, class Value>
546  Input::AbstractRecord field_record;
547  if (rec.opt_val(field.input_name(), field_record)) {
548  FieldAlgoBaseInitData init_data(field.input_name(), field.n_comp(), field.units(), field.limits());
549  return FieldBaseType::function_factory(field_record, init_data );
550  }
551  else
552  return FieldBasePtr();
553 }
554 
555 
556 template<int spacedim, class Value>
558  return in_rec.find<Input::AbstractRecord>(input_name);
559 }
560 
561 
562 
563 
564 template<int spacedim, class Value>
566  if (! flags().match(FieldFlag::declare_input)) return;
567 
568  // check that times forms ascending sequence
569  double time,last_time=0.0;
570 
572  it != list.end();
573  ++it) {
574  for(auto rit = factories_.rbegin() ; rit != factories_.rend(); ++rit) {
575  if ( (*rit)->is_active_field_descriptor( (*it), this->input_name() ) ) {
576  shared_->input_list_.push_back( Input::Record( *it ) );
577  time = it->val<double>("time");
578  if (time < last_time) {
579  THROW( ExcNonascendingTime()
580  << EI_Time(time)
581  << EI_Field(input_name())
582  << it->ei_address());
583  }
584  last_time = time;
585 
586  break;
587  }
588  }
589  }
590 
591 }
592 
593 
594 
595 template<int spacedim, class Value>
596 void Field<spacedim,Value>::compute_field_data(OutputTime::DiscreteSpace space_type, std::shared_ptr<OutputTime> stream) {
597  typedef typename Value::element_type ElemType;
598 
599  /* It's possible now to do output to the file only in the first process */
600  if( stream->get_rank() != 0) {
601  /* TODO: do something, when support for Parallel VTK is added */
602  return;
603  }
604 
605  ElementDataCache<ElemType> &output_data = stream->prepare_compute_data<ElemType>(this->name(), space_type,
606  (unsigned int)Value::NRows_, (unsigned int)Value::NCols_);
607 
608 
609  /* Copy data to array */
610  switch(space_type) {
611  case OutputTime::NODE_DATA: {
612  // set output data to zero
613  vector<unsigned int> count(output_data.n_values(), 0);
614  for(unsigned int idx=0; idx < output_data.n_values(); idx++)
615  output_data.zero(idx);
616 
617  std::shared_ptr<OutputMesh> output_mesh = std::dynamic_pointer_cast<OutputMesh>( stream->get_output_mesh_ptr() );
618  for(const auto & ele : *output_mesh )
619  {
620  std::vector<Space<3>::Point> vertices = ele.vertex_list();
621  for(unsigned int i=0; i < ele.n_nodes(); i++)
622  {
623  unsigned int node_index = ele.node_index(i);
624  const Value &node_value =
625  Value( const_cast<typename Value::return_type &>(
626  this->value(vertices[i],
627  ElementAccessor<spacedim>(ele.orig_mesh(), ele.orig_element_idx(),false) ))
628  );
629  output_data.add(node_index, node_value.mem_ptr() );
630  count[node_index]++;
631  }
632  }
633 
634  // Compute mean values at nodes
635  for(unsigned int idx=0; idx < output_data.n_values(); idx++)
636  output_data.normalize(idx, count[idx]);
637  }
638  break;
640  std::shared_ptr<OutputMeshDiscontinuous> output_mesh_disc
641  = std::dynamic_pointer_cast<OutputMeshDiscontinuous>( stream->get_output_mesh_ptr(true) );
642  for(const auto & ele : *output_mesh_disc )
643  {
644  std::vector<Space<3>::Point> vertices = ele.vertex_list();
645  for(unsigned int i=0; i < ele.n_nodes(); i++)
646  {
647  unsigned int node_index = ele.node_index(i);
648  const Value &node_value =
649  Value( const_cast<typename Value::return_type &>(
650  this->value(vertices[i],
651  ElementAccessor<spacedim>(ele.orig_mesh(), ele.orig_element_idx(),false) ))
652  );
653  ASSERT_EQ(output_data.n_elem(), node_value.n_rows()*node_value.n_cols()).error();
654  output_data.store_value(node_index, node_value.mem_ptr() );
655  }
656  }
657  }
658  break;
659  case OutputTime::ELEM_DATA: {
660  std::shared_ptr<OutputMesh> output_mesh = std::dynamic_pointer_cast<OutputMesh>( stream->get_output_mesh_ptr() );
661  for(const auto & ele : *output_mesh )
662  {
663  unsigned int ele_index = ele.idx();
664  const Value &ele_value =
665  Value( const_cast<typename Value::return_type &>(
666  this->value(ele.centre(),
667  ElementAccessor<spacedim>(ele.orig_mesh(), ele.orig_element_idx(),false))
668  )
669  );
670  ASSERT_EQ(output_data.n_elem(), ele_value.n_rows()*ele_value.n_cols()).error();
671  output_data.store_value(ele_index, ele_value.mem_ptr() );
672  }
673  }
674  break;
675  }
676 
677  /* Set the last time */
678  stream->update_time(this->time());
679 
680 }
681 
682 
683 
684 #endif /* FIELD_IMPL_HH_ */
Class represents output mesh with continuous elements.
Definition: output_mesh.hh:127
void check_initialized_region_fields_()
Definition: field.impl.hh:483
Classes for auxiliary output mesh.
Iterator< ValueType > begin() const
Common abstract parent of all Field<...> classes.
Definition: field_common.hh:60
virtual bool is_active_field_descriptor(const Input::Record &in_rec, const std::string &input_name)
Definition: field.impl.hh:557
pair< double, FieldBasePtr > HistoryPoint
Pair: time, pointer to FieldBase instance.
Definition: field.hh:311
bool is_jump_time_
Accessor to input data conforming to declared Array.
Definition: accessors.hh:567
unsigned int size() const
Number of subfields that compose the multi-field.
Definition: multi_field.hh:174
MakeInstanceReturnType make_instance(std::vector< ParameterPair > vec=std::vector< ParameterPair >()) override
Implements TypeBase::make_instance.
static const Input::Type::Instance & get_input_type_instance(Input::Type::Selection value_selection=Input::Type::Selection())
RegionSet union_set(std::vector< string > set_names) const
Definition: region.cc:472
Reader for (slightly) modified input files.
std::string get_value_attribute() const override
Definition: field.impl.hh:398
std::string name_
Class template representing a field with values dependent on: point, element, and region...
Definition: field.hh:62
std::string format(CStringRef format_str, ArgList args)
Definition: format.h:3141
unsigned int component_index_
std::pair< double, double > limits() const
Store data of one initialization message.
Definition: field_common.hh:75
void store_value(unsigned int idx, const T *value)
Definition: mesh.h:97
Iterator< Ret > find(const string &key) const
void update_history(const TimeStep &time)
Definition: field.impl.hh:412
Helper class that stores data of generic types.
Definition: type_generic.hh:89
void set_input_list(const Input::Array &list) override
Definition: field.impl.hh:565
Helper struct stores data for initizalize descentants of FieldAlgorithmBase.
void observe_output(std::shared_ptr< Observe > observe) override
Definition: field.impl.hh:350
double last_time_
const std::string & input_default() const
bool set_time(const TimeStep &time, LimitSide limit_side) override
Definition: field.impl.hh:238
const RegionDB & region_db() const
Definition: mesh.h:155
#define ASSERT(expr)
Allow use shorter versions of macro names if these names is not used with external library...
Definition: asserts.hh:346
void field_output(std::shared_ptr< OutputTime > stream) override
Definition: field.impl.hh:333
Class for declaration of the integral input data.
Definition: type_base.hh:489
virtual FieldBasePtr create_field(Input::Record rec, const FieldCommon &field)
Definition: field.impl.hh:545
IT::Instance get_input_type() override
Definition: field.impl.hh:132
FieldCommon & units(const UnitSI &units)
Set basic units of the field.
virtual void value_list(const std::vector< Point > &point_list, const ElementAccessor< spacedim > &elm, std::vector< typename Value::return_type > &value_list) const
Definition: field.hh:376
Field()
Definition: field.impl.hh:38
Class for declaration of inputs sequences.
Definition: type_base.hh:345
std::shared_ptr< SharedData > data_
Definition: field.hh:325
static constexpr bool value
Definition: json.hpp:87
constexpr bool match(Mask mask) const
Definition: flag_array.hh:163
std::shared_ptr< SharedData > shared_
IteratorBase end() const
void add(unsigned int idx, const T *value)
unsigned int DiscreteSpaceFlags
Definition: output_time.hh:106
OutputTime::DiscreteSpace output_type() const
EI_Address ei_address() const
Definition: accessors.cc:178
#define OLD_ASSERT(...)
Definition: global_defs.h:131
Class represents output mesh with discontinuous elements.
Definition: output_mesh.hh:149
bool opt_val(const string &key, Ret &value) const
double time() const
const std::string & name() const
bool ge(double other_time) const
unsigned int FieldEnum
Definition: field_values.hh:43
FieldFlag::Flags & flags()
Region find_id(unsigned int id, unsigned int dim) const
Definition: region.cc:180
const UnitSI & units() const
std::vector< string > get_and_check_operands(const Input::Array &operands) const
Definition: region.cc:312
T get_root_interface() const
Returns the root accessor.
Accessor to the data with type Type::Record.
Definition: accessors.hh:292
IT::Array get_multifield_input_type() override
Definition: field.impl.hh:139
void zero(unsigned int idx)
#define xprintf(...)
Definition: system.hh:92
std::shared_ptr< ControlField > no_check_control_field_
Definition: field.hh:335
#define OLD_ASSERT_LESS(a, b)
Definition: global_defs.h:134
static const unsigned int N_DISCRETE_SPACES
Definition: output_time.hh:95
virtual Value::return_type const & value(const Point &p, const ElementAccessor< spacedim > &elm) const
Definition: field.hh:362
LimitSide last_limit_side_
double end() const
std::vector< FieldBasePtr > region_fields_
Definition: field.hh:340
Accessor to the polymorphic input data of a type given by an AbstracRecord object.
Definition: accessors.hh:459
void normalize(unsigned int idx, unsigned int divisor)
FieldResult
FieldResult field_result(RegionSet region_set) const override
Indicates special field states.
Definition: field.impl.hh:375
Definition: system.hh:64
bool is_jump_time()
static std::shared_ptr< FieldAlgorithmBase< spacedim, Value > > function_factory(const Input::AbstractRecord &rec, const struct FieldAlgoBaseInitData &init_data)
std::shared_ptr< FieldBaseType > FieldBasePtr
Definition: field.hh:66
std::vector< std::shared_ptr< FactoryBase > > factories_
Definition: field.hh:342
auto disable_where(const Field< spacedim, typename FieldValue< spacedim >::Enum > &control_field, const vector< FieldEnum > &value_list) -> Field &
Definition: field.impl.hh:149
static std::vector< MessageData > messages_data_
Vector of data of initialization messages.
boost::circular_buffer< HistoryPoint > RegionHistory
Nearest history of one region.
Definition: field.hh:313
void set_component_index(unsigned int idx)
bool is_constant(Region reg) override
Definition: field.impl.hh:189
void add_factory(std::shared_ptr< FactoryBase > factory)
Definition: field.impl.hh:539
void set_field(const RegionSet &domain, FieldBasePtr field, double time=0.0)
Definition: field.impl.hh:198
#define ASSERT_LT(a, b)
Definition of comparative assert macro (Less Than)
Definition: asserts.hh:295
Class OutputElement and its iterator OutputElementIterator on the output mesh.
bool gt(double other_time) const
const Mesh * mesh() const
FieldCommon & name(const string &name)
Definition: field_common.hh:97
unsigned int n_comp() const
#define OLD_ASSERT_EQUAL(a, b)
Definition: global_defs.h:133
bool changed() const
void set_mesh(const Mesh &mesh) override
Definition: field.impl.hh:159
void set_history_changed()
bool is_valid() const
Returns false if the region has undefined/invalid value.
Definition: region.hh:77
const std::string & input_name() const
void copy_from(const FieldCommon &other) override
Definition: field.impl.hh:316
static constexpr Mask equation_input
The field is data parameter of the owning equation. (default on)
Definition: field_flag.hh:33
bool is_bc() const
void compute_field_data(OutputTime::DiscreteSpace space_type, std::shared_ptr< OutputTime > stream)
Definition: field.impl.hh:596
#define THROW(whole_exception_expr)
Wrapper for throw. Saves the throwing point.
Definition: exceptions.hh:53
Representation of one time step..
TimeStatus set_time_result_
Field & operator=(const Field &other)
Definition: field.impl.hh:97
static const unsigned int history_length_limit_
LimitSide
Definition: field_common.hh:47
#define ASSERT_EQ(a, b)
Definition of comparative assert macro (EQual)
Definition: asserts.hh:327
static constexpr Mask declare_input
The field can be set from input. The key in input field descriptor is declared. (default on) ...
Definition: field_flag.hh:35
unsigned int idx() const
Returns a global index of the region.
Definition: region.hh:81