Flow123d  3.9.0-9663d1cde
fe_value_handler.cc
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 fe_value_handler.cc
15  * @brief
16  */
17 
19 #include "la/vector_mpi.hh"
20 #include "fem/mapping_p1.hh"
21 #include "fem/fe_values.hh"
22 #include "quadrature/quadrature.hh"
24 #include "mesh/bounding_box.hh"
25 #include "mesh/accessors.hh"
26 #include "fem/fe_values_views.hh"
27 #include "fem/dh_cell_accessor.hh"
28 
29 
30 /**
31  * Helper class, allow to simplify computing value of FieldFE.
32  *
33  * Use correct method FEValues<...>::shape_xxx given with Value::rank_.
34  * Is done by class partial specialization as, we were not able to do this using function overloading (since
35  * they differ only by return value) and partial specialization of the function templates is not supported in C++.
36  */
37 template<int rank, int spacedim, class Value>
39 public:
40 
41  inline static typename Value::return_type fe_value(FEValues<spacedim> &fe_val, unsigned int i_dof, unsigned int i_qp, unsigned int comp_index)
42  {
43  ASSERT_PERMANENT(false).error("Unsupported format of FieldFE!\n");
44  typename Value::return_type ret;
45  Value val(ret);
46  val.zeros();
47  return ret;
48  }
49 };
50 
51 
52 /// Partial template specialization of FEShapeHandler for scalar fields
53 template<int spacedim, class Value>
54 class FEShapeHandler<0, spacedim, Value> {
55 public:
56  inline static typename Value::return_type fe_value(FEValues<3> &fe_val, unsigned int i_dof, unsigned int i_qp, FMT_UNUSED unsigned int comp_index)
57  {
58  return fe_val.scalar_view(comp_index).value(i_dof, i_qp);
59  }
60 };
61 
62 
63 /// Partial template specialization of FEShapeHandler for vector fields
64 template<int spacedim, class Value>
65 class FEShapeHandler<1, spacedim, Value> {
66 public:
67  inline static typename Value::return_type fe_value(FEValues<3> &fe_val, unsigned int i_dof, unsigned int i_qp, unsigned int comp_index)
68  {
69  return fe_val.vector_view(comp_index).value(i_dof, i_qp);
70  }
71 };
72 
73 
74 /// Partial template specialization of FEShapeHandler for tensor fields
75 template<int spacedim, class Value>
76 class FEShapeHandler<2, spacedim, Value> {
77 public:
78  inline static typename Value::return_type fe_value(FEValues<3> &fe_val, unsigned int i_dof, unsigned int i_qp, unsigned int comp_index)
79  {
80  return fe_val.tensor_view(comp_index).value(i_dof, i_qp);
81  }
82 };
83 
84 
85 
86 template <int elemdim, int spacedim, class Value>
88 : value_(r_value_)
89 {}
90 
91 
92 template <int elemdim, int spacedim, class Value>
94 {
95  if (dh_)
96  WarningOut() << "Multiple initialization of FEValueHandler!";
97 
98  dh_ = init_data.dh;
99  data_vec_ = init_data.data_vec;
100  value_.set_n_comp(init_data.n_comp);
101  range_begin_ = init_data.range_begin;
102  range_end_ = init_data.range_end;
103  fe_ = init_data.mixed_fe[Dim<elemdim>{}];
104 }
105 
106 
107 template <int elemdim, int spacedim, class Value> inline
108 typename Value::return_type const &FEValueHandler<elemdim, spacedim, Value>::value(const Point &p, const ElementAccessor<spacedim> &elm)
109 {
110  Armor::array point_list(spacedim, 1, 1);
111  point_list.set(0) = Armor::ArmaVec<double,spacedim>( p );
113  v_list.push_back(r_value_);
114  this->value_list(point_list, elm, v_list);
115  this->r_value_ = v_list[0];
116  return this->r_value_;
117 }
118 
119 
120 template <int elemdim, int spacedim, class Value>
123 {
124  ASSERT_EQ( point_list.size(), value_list.size() ).error();
125 
126  const DHCellAccessor cell = dh_->cell_accessor_from_element( elm.idx() );
127  LocDofVec loc_dofs;
128  if (boundary_dofs_) loc_dofs = this->get_loc_dof_indices(elm.idx());
129  else loc_dofs = cell.get_loc_dof_indices();
130 
131  // map points to reference cell, create quadrature and FEValues object
133  Quadrature quad(elemdim, point_list.size());
134  for (unsigned int k=0; k<point_list.size(); k++)
136 
137  FEValues<spacedim> fe_values(quad, *fe_, update_values);
138  fe_values.reinit( elm );
139 
140  for (unsigned int k=0; k<point_list.size(); k++) {
141  Value envelope(value_list[k]);
142  envelope.zeros();
143  for (unsigned int i=this->range_begin_, i_dof=0; i<this->range_end_; i++, i_dof++) {
144  value_list[k] += data_vec_.get(loc_dofs[i])
146  }
147  }
148 }
149 
150 
151 template <int elemdim, int spacedim, class Value>
152 unsigned int FEValueHandler<elemdim, spacedim, Value>::compute_quadrature(std::vector<arma::vec::fixed<3>> & q_points, std::vector<double> & q_weights,
153  const ElementAccessor<spacedim> &ele, unsigned int order)
154 {
155  static const double weight_coefs[] = { 1., 1., 2., 6. };
156 
157  QGauss qgauss(elemdim, order);
159 
160  for(unsigned i=0; i<qgauss.size(); ++i) {
161  q_weights[i] = qgauss.weight(i)*weight_coefs[elemdim];
163  }
164 
165  return qgauss.size();
166 }
167 
168 
169 template <int spacedim, class Value>
171 {
172  if (dh_)
173  WarningOut() << "Multiple initialization of FEValueHandler!";
174 
175  dh_ = init_data.dh;
176  data_vec_ = init_data.data_vec;
177  value_.set_n_comp(init_data.n_comp);
178  range_begin_ = init_data.range_begin;
179  range_end_ = init_data.range_end;
180 }
181 
182 
183 template <int spacedim, class Value>
186 {
187  ASSERT_EQ( point_list.size(), value_list.size() ).error();
188 
189  const DHCellAccessor cell = dh_->cell_accessor_from_element( elm.idx() );
190  LocDofVec loc_dofs;
191  if (boundary_dofs_) loc_dofs = this->get_loc_dof_indices(elm.idx());
192  else loc_dofs = cell.get_loc_dof_indices();
193 
194  for (unsigned int k=0; k<point_list.size(); k++) {
195  Value envelope(value_list[k]);
196  envelope.zeros();
197  for (unsigned int i=this->range_begin_; i<this->range_end_; i++) {
198  envelope(i / envelope.n_cols(), i % envelope.n_rows()) += data_vec_.get(loc_dofs[i]);
199  }
200  }
201 }
202 
203 
204 template <int elemdim, int spacedim, class Value>
206 {
207 }
208 
209 
210 // Instantiations of FEValueHandler and FEShapeHandler
211 #define INSTANCE_VALUE_HANDLER_ALL(dim, spacedim) \
212 template class FEValueHandler<dim, spacedim, FieldValue<0>::Enum >; \
213 template class FEValueHandler<dim, spacedim, FieldValue<0>::Integer >; \
214 template class FEValueHandler<dim, spacedim, FieldValue<0>::Scalar >; \
215 template class FEValueHandler<dim, spacedim, FieldValue<spacedim>::VectorFixed >; \
216 template class FEValueHandler<dim, spacedim, FieldValue<spacedim>::TensorFixed >;
217 
218 #define INSTANCE_VALUE_HANDLER(dim) \
219 INSTANCE_VALUE_HANDLER_ALL(dim,3)
220 //INSTANCE_VALUE_HANDLER_ALL(dim,2)
221 
226 
227 template class FEShapeHandler<0, 3, FieldValue<0>::Enum >;
228 template class FEShapeHandler<0, 3, FieldValue<0>::Integer >;
229 template class FEShapeHandler<0, 3, FieldValue<0>::Scalar >;
230 template class FEShapeHandler<1, 3, FieldValue<3>::VectorFixed >;
231 template class FEShapeHandler<2, 3, FieldValue<3>::TensorFixed >;
FEValueHandler::~FEValueHandler
~FEValueHandler()
Destructor.
Definition: fe_value_handler.cc:205
LocDofVec
arma::Col< IntIdx > LocDofVec
Definition: index_types.hh:28
FEValueInitData::range_end
unsigned int range_end
Holds end of component range of evaluation.
Definition: fe_value_handler.hh:48
Quadrature::point
Armor::ArmaVec< double, point_dim > point(unsigned int i) const
Returns the ith quadrature point.
Definition: quadrature.hh:91
FEValueHandler::get_loc_dof_indices
LocDofVec get_loc_dof_indices(unsigned int cell_idx) const
TODO: Temporary solution. Fix problem with merge new DOF handler and boundary Mesh....
Definition: fe_value_handler.hh:85
FEShapeHandler
Definition: fe_value_handler.cc:38
FEValueHandler< 3, spacedim, Value >::Point
Space< spacedim >::Point Point
Definition: fe_value_handler.hh:60
FEValues::vector_view
const FEValuesViews::Vector< spacedim > & vector_view(unsigned int i) const
Accessor to vector values of multicomponent FE.
Definition: fe_values.hh:277
fe_values_views.hh
vector_mpi.hh
RefElement
Definition: ref_element.hh:339
FEValueHandler::initialize
void initialize(FEValueInitData init_data)
Initialize data members.
Definition: fe_value_handler.cc:93
Armor::Array::vec
ArmaVec< Type, nr > vec(uint mat_index) const
Definition: armor.hh:821
fe_values.hh
Class FEValues calculates finite element data on the actual cells such as shape function values,...
update_values
@ update_values
Shape function values.
Definition: update_flags.hh:87
Quadrature::size
unsigned int size() const
Returns number of quadrature points.
Definition: quadrature.hh:86
std::vector
Definition: doxy_dummy_defs.hh:7
ElementAccessor
Definition: dh_cell_accessor.hh:32
Dim
Definition: mixed.hh:25
FEValues
Calculates finite element data on the actual cell.
Definition: fe_values.hh:66
FEValueInitData::mixed_fe
MixedPtr< FiniteElement > mixed_fe
FiniteElement objects of all dimensions.
Definition: fe_value_handler.hh:50
MappingP1::project_unit_to_real
static RealPoint project_unit_to_real(const BaryPoint &point, const ElementMap &map)
Definition: mapping_p1.cc:85
FEValueHandler::dh_
std::shared_ptr< DOFHandlerMultiDim > dh_
DOF handler object.
Definition: fe_value_handler.hh:95
dh_cell_accessor.hh
Armor::mat
ArmaMat< double, N, M > mat
Definition: armor.hh:888
accessors.hh
FEValueInitData::dh
std::shared_ptr< DOFHandlerMultiDim > dh
DOF handler object.
Definition: fe_value_handler.hh:38
ASSERT_PERMANENT
#define ASSERT_PERMANENT(expr)
Allow use shorter versions of macro names if these names is not used with external library.
Definition: asserts.hh:348
quadrature_lib.hh
Definitions of particular quadrature rules on simplices.
FEValueHandler::range_end_
unsigned int range_end_
End of dof range of actual component.
Definition: fe_value_handler.hh:104
RefElement::bary_to_local
static LocalPoint bary_to_local(const BaryPoint &bp)
Converts from barycentric to local coordinates.
Definition: ref_element.cc:201
Quadrature::set
Armor::Array< double >::ArrayMatSet set(uint i)
Definition: quadrature.hh:97
Quadrature::weight
double weight(unsigned int i) const
Returns the ith weight.
Definition: quadrature.hh:107
FEShapeHandler< 0, spacedim, Value >::fe_value
static Value::return_type fe_value(FEValues< 3 > &fe_val, unsigned int i_dof, unsigned int i_qp, FMT_UNUSED unsigned int comp_index)
Definition: fe_value_handler.cc:56
ASSERT_EQ
#define ASSERT_EQ(a, b)
Definition of comparative assert macro (EQual) only for debug mode.
Definition: asserts.hh:333
FEShapeHandler< 1, spacedim, Value >::fe_value
static Value::return_type fe_value(FEValues< 3 > &fe_val, unsigned int i_dof, unsigned int i_qp, unsigned int comp_index)
Definition: fe_value_handler.cc:67
FEValueHandler::data_vec_
VectorMPI data_vec_
Store data of Field.
Definition: fe_value_handler.hh:97
FEShapeHandler< 2, spacedim, Value >::fe_value
static Value::return_type fe_value(FEValues< 3 > &fe_val, unsigned int i_dof, unsigned int i_qp, unsigned int comp_index)
Definition: fe_value_handler.cc:78
FEValueHandler::value_
Value value_
Last value, prevents passing large values (vectors) by value.
Definition: fe_value_handler.hh:99
FEValueHandler::compute_quadrature
unsigned int compute_quadrature(std::vector< arma::vec::fixed< 3 >> &q_points, std::vector< double > &q_weights, const ElementAccessor< spacedim > &elm, unsigned int order=3)
Compute real coordinates and weights (use QGauss) for given element.
Definition: fe_value_handler.cc:152
bounding_box.hh
Armor::Array::set
ArrayMatSet set(uint index)
Definition: armor.hh:838
Armor::Array::size
unsigned int size() const
Definition: armor.hh:728
FEValueInitData
Initialization structure of FEValueHandler class.
Definition: fe_value_handler.hh:35
FEValues::tensor_view
const FEValuesViews::Tensor< spacedim > & tensor_view(unsigned int i) const
Accessor to tensor values of multicomponent FE.
Definition: fe_values.hh:287
QGauss
Symmetric Gauss-Legendre quadrature formulae on simplices.
Definition: quadrature_lib.hh:34
Value
@ Value
Definition: finite_element.hh:43
FEValueHandler::FEValueHandler
FEValueHandler()
Constructor.
Definition: fe_value_handler.cc:87
MappingP1::element_map
static ElementMap element_map(ElementAccessor< 3 > elm)
Definition: mapping_p1.cc:48
DHCellAccessor
Cell accessor allow iterate over DOF handler cells.
Definition: dh_cell_accessor.hh:43
WarningOut
#define WarningOut()
Macro defining 'warning' record of log.
Definition: logger.hh:278
fe_value_handler.hh
FEValueHandler::value
const Value::return_type & value(const Point &p, const ElementAccessor< spacedim > &elm)
Returns one value in one given point.
Definition: fe_value_handler.cc:108
MappingP1
Affine mapping between reference and actual cell.
Definition: mapping_p1.hh:58
FEValues::scalar_view
const FEValuesViews::Scalar< spacedim > & scalar_view(unsigned int i) const
Accessor to scalar values of multicomponent FE.
Definition: fe_values.hh:267
quadrature.hh
Basic definitions of numerical quadrature rules.
FEValueHandler::range_begin_
unsigned int range_begin_
Begin of dof range of actual component.
Definition: fe_value_handler.hh:102
DHCellAccessor::get_loc_dof_indices
LocDofVec get_loc_dof_indices() const
Returns the local indices of dofs associated to the cell on the local process.
Definition: dh_cell_accessor.hh:88
Armor::Array< double >
FEValueInitData::data_vec
VectorMPI data_vec
Store data of Field.
Definition: fe_value_handler.hh:40
ElementAccessor::idx
unsigned int idx() const
We need this method after replacing Region by RegionIdx, and movinf RegionDB instance into particular...
Definition: accessors.hh:215
FEShapeHandler::fe_value
static Value::return_type fe_value(FEValues< spacedim > &fe_val, unsigned int i_dof, unsigned int i_qp, unsigned int comp_index)
Definition: fe_value_handler.cc:41
mapping_p1.hh
Class MappingP1 implements the affine transformation of the unit cell onto the actual cell.
VectorMPI::get
double get(unsigned int pos) const
Return value on given position.
Definition: vector_mpi.hh:105
FEValueHandler::value_list
void value_list(const Armor::array &point_list, const ElementAccessor< spacedim > &elm, std::vector< typename Value::return_type > &value_list)
Returns std::vector of scalar values in several points at once.
Definition: fe_value_handler.cc:121
FEValues::reinit
void reinit(const ElementAccessor< spacedim > &cell)
Update cell-dependent data (gradients, Jacobians etc.)
Definition: fe_values.cc:536
FEValueInitData::range_begin
unsigned int range_begin
Holds begin of component range of evaluation.
Definition: fe_value_handler.hh:46
INSTANCE_VALUE_HANDLER
#define INSTANCE_VALUE_HANDLER(dim)
Definition: fe_value_handler.cc:218
Quadrature
Base class for quadrature rules on simplices in arbitrary dimensions.
Definition: quadrature.hh:48
Armor::ArmaVec
typename arma::Col< Type >::template fixed< nr > ArmaVec
Definition: armor.hh:505
FEValueHandler::boundary_dofs_
std::shared_ptr< std::vector< IntIdx > > boundary_dofs_
Definition: fe_value_handler.hh:113
FEValueInitData::n_comp
unsigned int n_comp
number of components
Definition: fe_value_handler.hh:44
FieldValue
Definition: field_values.hh:645
FMT_UNUSED
#define FMT_UNUSED
Definition: posix.h:75