dune-pdelab  2.7-git
weightedsum.hh
Go to the documentation of this file.
1 // -*- tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*-
2 // vi: set et ts=8 sw=2 sts=2:
3 #ifndef DUNE_PDELAB_LOCALOPERATOR_WEIGHTEDSUM_HH
4 #define DUNE_PDELAB_LOCALOPERATOR_WEIGHTEDSUM_HH
5 
6 #include <dune/common/concept.hh>
8 
9 namespace Dune {
10  namespace PDELab {
14 
16 
25  template<typename K, typename... Args>
27  public CombinedOperator<WeightedSumLocalOperator<K, Args...>, Args...>
28  {
29  protected:
30  using Base = CombinedOperator<WeightedSumLocalOperator<K, Args...>, Args...>;
31  using ArgPtrs = typename Base::ArgPtrs;
32  using ArgRefs = typename Base::ArgRefs;
33  friend Base;
34 
35  using Weights = FieldVector<K, sizeof...(Args)>;
37 
38  // concept check for a weighted container, like e.g. LocalVector or LocalMatrix
40  template<class C>
41  auto require(C& c) -> decltype(
42  Concept::requireType<typename C::weight_type>(),
43  const_cast<C&>(c).weight()
44  // c.setWeight(std::declval<typename C::weight_type>())
45  );
46  };
47 
48  template<typename... FArgs>
49  void getWeights(FieldVector<K, sizeof...(FArgs)> & aweights,
50  std::tuple<FArgs...> fargs) const
51  {
52  Hybrid::forEach(std::make_index_sequence<sizeof...(FArgs)>{},
53  [&](auto j){
54  const auto & a = get<j>(fargs);
55  Hybrid::ifElse(models<WeightedContainer,decltype(a)>(),
56  [&](auto id){
57  aweights[j] = id(a).weight();});
58  });
59  }
60 
61  template<typename... FArgs>
62  void setWeights(const FieldVector<K, sizeof...(FArgs)> & aweights,
63  std::tuple<FArgs...> fargs) const
64  {
65  Hybrid::forEach(std::make_index_sequence<sizeof...(FArgs)>{},
66  [&](auto j){
67  auto & a = get<j>(fargs);
68  Hybrid::ifElse(models<WeightedContainer,decltype(a)>(),
69  [&](auto id){
70  id(a).setWeight(aweights[j]);});
71  });
72  }
73 
74  template<typename F, typename... FArgs>
75  void applyLops(F && f, FArgs &... fargs) const
76  {
77  // remember weights
78  FieldVector<K, sizeof...(FArgs)> aweights(K(0));
79  FieldVector<K, sizeof...(FArgs)> current_weights;
80  getWeights(aweights, std::forward_as_tuple(fargs...));
81  Hybrid::forEach(std::make_index_sequence<sizeof...(Args)>{},
82  [&](auto i){
83  if(weights[i] != K(0)) {
84  // set weights
85  current_weights = aweights;
86  current_weights *= weights[i];
87  setWeights(current_weights, std::forward_as_tuple(fargs...));
88  f(*Hybrid::elementAt(this->lops, i), fargs...);}}
89  );
90  // reset weights
91  setWeights(aweights, std::forward_as_tuple(fargs...));
92  }
93 
94  public:
96  //
99  //
100 
102 
106  WeightedSumLocalOperator (const Weights& weights_ = Weights(1))
107  : weights(weights_)
108  { }
109 
112  WeightedSumLocalOperator (Args&... lops_,
113  const Weights& weights_ = Weights(1))
114  : Base(lops_...), weights(weights_)
115  { }
116 
119  WeightedSumLocalOperator (Args&&... lops_,
120  const Weights& weights_ = Weights(1))
121  : Base(std::forward<Args>(lops_)...), weights(weights_)
122  { }
123 
124  protected:
126  : Base(std::forward<ArgPtrs>(lops)), weights(weights_)
127  { }
128 
129  public:
131  void setWeight(K w, std::size_t i)
132  { weights[i] = w; }
133 
135  K getWeight(std::size_t i)
136  { return weights[i]; }
137 
139  };
140 
142 
152  template<typename K, typename... Args>
153  class WeightedSumLocalOperator<K, std::tuple<Args...>> :
154  public WeightedSumLocalOperator<K, Args...>
155  {
156  using Base = WeightedSumLocalOperator<K, Args...>;
157  using ArgRefs = typename Base::ArgRefs;
158  using Weights = typename Base::Weights;
159 
160  public:
162 
166  [[deprecated("The specialization WeightedSumLocalOperator<K,Tuple<...>> is"
167  "deprecated and will be removed after PDELab 2.7.")]]
168  WeightedSumLocalOperator (const Weights& weights_ = Weights(1))
169  : Base(weights_)
170  { }
171 
173  [[deprecated("The specialization WeightedSumLocalOperator<K,Tuple<...>> is"
174  "deprecated and will be removed after PDELab 2.7.")]]
175  WeightedSumLocalOperator (const ArgRefs& lops_, const Weights& weights_ = Weights(1))
176  : Base(genericTransformTuple(lops_,
177  [](auto & l){return stackobject_to_shared_ptr(l);}), weights_)
178  { }
179  };
180 
181  }
182 }
183 
184 #endif // DUNE_PDELAB_LOCALOPERATOR_WEIGHTEDSUM_HH
Dune::PDELab::WeightedSumLocalOperator< K, Args... >::Weights
FieldVector< K, sizeof...(Args)> Weights
Definition: weightedsum.hh:35
Dune::PDELab::WeightedSumLocalOperator::WeightedContainer
Definition: weightedsum.hh:39
Dune::PDELab::WeightedSumLocalOperator::applyLops
void applyLops(F &&f, FArgs &... fargs) const
Definition: weightedsum.hh:75
sum.hh
Dune::PDELab::WeightedSumLocalOperator::WeightedSumLocalOperator
WeightedSumLocalOperator(const Weights &weights_=Weights(1))
construct a WeightedSumLocalOperator
Definition: weightedsum.hh:106
Dune::PDELab::WeightedSumLocalOperator::WeightedContainer::require
auto require(C &c) -> decltype(Concept::requireType< typename C::weight_type >(), const_cast< C & >(c).weight())
Dune::PDELab::WeightedSumLocalOperator::getWeight
K getWeight(std::size_t i)
get the weight for the i'th component of the sum
Definition: weightedsum.hh:135
Dune::PDELab::CombinedOperator< WeightedSumLocalOperator< K, Args... >, Args... >::ArgRefs
std::tuple< Args &... > ArgRefs
Definition: combinedoperator.hh:33
Dune
For backward compatibility – Do not use this!
Definition: adaptivity.hh:28
Dune::PDELab::WeightedSumLocalOperator::WeightedSumLocalOperator
WeightedSumLocalOperator(ArgPtrs &&lops, const Weights &weights_)
Definition: weightedsum.hh:125
Dune::PDELab::WeightedSumLocalOperator::WeightedSumLocalOperator
WeightedSumLocalOperator(Args &... lops_, const Weights &weights_=Weights(1))
Definition: weightedsum.hh:112
Dune::PDELab::WeightedSumLocalOperator::getWeights
void getWeights(FieldVector< K, sizeof...(FArgs)> &aweights, std::tuple< FArgs... > fargs) const
Definition: weightedsum.hh:49
Dune::PDELab::WeightedSumLocalOperator< K, std::tuple< Args... > >::WeightedSumLocalOperator
WeightedSumLocalOperator(const ArgRefs &lops_, const Weights &weights_=Weights(1))
construct a WeightedSumLocalOperator from a tuple of local operators
Definition: weightedsum.hh:175
Dune::PDELab::WeightedSumLocalOperator::setWeights
void setWeights(const FieldVector< K, sizeof...(FArgs)> &aweights, std::tuple< FArgs... > fargs) const
Definition: weightedsum.hh:62
Dune::PDELab::CombinedOperator< WeightedSumLocalOperator< K, Args... >, Args... >::lops
ArgPtrs lops
Definition: combinedoperator.hh:35
Dune::PDELab::CombinedOperator
A local operator to take combine different local operators.
Definition: combinedoperator.hh:29
Dune::PDELab::WeightedSumLocalOperator::WeightedSumLocalOperator
WeightedSumLocalOperator(Args &&... lops_, const Weights &weights_=Weights(1))
Definition: weightedsum.hh:119
Dune::PDELab::WeightedSumLocalOperator
A local operator to take the weighted sum of other local operators.
Definition: weightedsum.hh:26
Dune::PDELab::WeightedSumLocalOperator::weights
Weights weights
Definition: weightedsum.hh:36
Dune::PDELab::WeightedSumLocalOperator::Base
friend Base
Definition: weightedsum.hh:33
Dune::PDELab::WeightedSumLocalOperator::setWeight
void setWeight(K w, std::size_t i)
set the weight for the i'th component of the sum
Definition: weightedsum.hh:131
Dune::PDELab::CombinedOperator< WeightedSumLocalOperator< K, Args... >, Args... >::ArgPtrs
std::tuple< std::shared_ptr< std::remove_reference_t< Args > >... > ArgPtrs
Definition: combinedoperator.hh:32
w
VTKWriter & w
Definition: function.hh:842
Dune::PDELab::WeightedSumLocalOperator< K, std::tuple< Args... > >::WeightedSumLocalOperator
WeightedSumLocalOperator(const Weights &weights_=Weights(1))
construct a WeightedSumLocalOperator
Definition: weightedsum.hh:168