Loading [MathJax]/extensions/tex2jax.js
ug4
All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Modules Pages
scale_add_linker_impl.h
Go to the documentation of this file.
1/*
2 * Copyright (c) 2012-2015: G-CSC, Goethe University Frankfurt
3 * Author: Andreas Vogel
4 *
5 * This file is part of UG4.
6 *
7 * UG4 is free software: you can redistribute it and/or modify it under the
8 * terms of the GNU Lesser General Public License version 3 (as published by the
9 * Free Software Foundation) with the following additional attribution
10 * requirements (according to LGPL/GPL v3 §7):
11 *
12 * (1) The following notice must be displayed in the Appropriate Legal Notices
13 * of covered and combined works: "Based on UG4 (www.ug4.org/license)".
14 *
15 * (2) The following notice must be displayed at a prominent place in the
16 * terminal output of covered works: "Based on UG4 (www.ug4.org/license)".
17 *
18 * (3) The following bibliography is recommended for citation and must be
19 * preserved in all covered files:
20 * "Reiter, S., Vogel, A., Heppner, I., Rupp, M., and Wittum, G. A massively
21 * parallel geometric multigrid solver on hierarchically distributed grids.
22 * Computing and visualization in science 16, 4 (2013), 151-164"
23 * "Vogel, A., Reiter, S., Rupp, M., Nägel, A., and Wittum, G. UG4 -- a novel
24 * flexible software system for simulating pde based models on high performance
25 * computers. Computing and visualization in science 16, 4 (2013), 165-179"
26 *
27 * This program is distributed in the hope that it will be useful,
28 * but WITHOUT ANY WARRANTY; without even the implied warranty of
29 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
30 * GNU Lesser General Public License for more details.
31 */
32
33#ifndef __H__UG__LIB_DISC__SPATIAL_DISC__SCALE_ADD_LINKER_IMPL__
34#define __H__UG__LIB_DISC__SPATIAL_DISC__SCALE_ADD_LINKER_IMPL__
35
36#include "scale_add_linker.h"
37#include "linker_traits.h"
39
40namespace ug{
41
43// ScaleAddLinker
45
46template <typename TData, int dim, typename TDataScale, typename TRet>
48ScaleAddLinker(const ScaleAddLinker& linker)
49{
50 if(linker.m_vpUserData.size() != linker.m_vpScaleData.size())
51 UG_THROW("ScaleAddLinker: number of scaling factors and data mismatch.");
52
53 for(size_t i = 0; i < linker.m_vpUserData.size(); ++i)
54 {
55 this->add(linker.m_vpScaleData[i], linker.m_vpUserData[i]);
56 }
57}
58
59
60template <typename TData, int dim, typename TDataScale, typename TRet>
63{
64// current number of inputs
65 const size_t numInput = base_type::num_input() / 2;
66
67// resize scaling
68 m_vpUserData.resize(numInput+1);
69 m_vpDependData.resize(numInput+1);
70 m_vpScaleData.resize(numInput+1);
71 m_vpScaleDependData.resize(numInput+1);
72
73// remember userdata
74 UG_ASSERT(data.valid(), "Null Pointer as Input set.");
75 m_vpUserData[numInput] = data;
76 m_vpDependData[numInput] = data.template cast_dynamic<DependentUserData<TData, dim> >();
77
78// remember userdata
79 UG_ASSERT(scale.valid(), "Null Pointer as Scale set.");
80 m_vpScaleData[numInput] = scale;
81 m_vpScaleDependData[numInput] = scale.template cast_dynamic<DependentUserData<TDataScale, dim> >();
82
83// increase number of inputs by one and set inputs at base class
84 base_type::set_num_input(2*numInput+2);
85 base_type::set_input(2*numInput, data, data);
86 base_type::set_input(2*numInput+1, scale, scale);
87}
88
89template <typename TData, int dim, typename TDataScale, typename TRet>
92{
93 add(CreateConstUserData<dim>(scale, TDataScale()), data);
94}
95
96template <typename TData, int dim, typename TDataScale, typename TRet>
99{
100 add(scale, CreateConstUserData<dim>(data, TData()));
101}
102
103template <typename TData, int dim, typename TDataScale, typename TRet>
105add(number scale, number data)
106{
107 add(CreateConstUserData<dim>(scale, TDataScale()),
108 CreateConstUserData<dim>(data, TData()));
109}
110
111
112template <typename TData, int dim, typename TDataScale, typename TRet>
114evaluate (TRet& value,
115 const MathVector<dim>& globIP,
116 number time, int si) const
117{
118 // reset value
119 value = 0.0;
120
121 TData valData;
122 TDataScale valScale;
123
124// add contribution of each summand
125 for(size_t c = 0; c < m_vpUserData.size(); ++c)
126 {
127 (*m_vpUserData[c])(valData, globIP, time, si);
128 (*m_vpScaleData[c])(valScale, globIP, time, si);
129
131 mult_add(value, valData, valScale);
132 }
133}
134
135template <typename TData, int dim, typename TDataScale, typename TRet>
136template <int refDim>
138evaluate(TRet vValue[],
139 const MathVector<dim> vGlobIP[],
140 number time, int si,
141 GridObject* elem,
142 const MathVector<dim> vCornerCoords[],
143 const MathVector<refDim> vLocIP[],
144 const size_t nip,
145 LocalVector* u,
146 const MathMatrix<refDim, dim>* vJT) const
147{
148 // reset value
149 for(size_t ip = 0; ip < nip; ++ip)
150 vValue[ip] = 0.0;
151
152 std::vector<TData> vValData(nip);
153 std::vector<TDataScale> vValScale(nip);
154
155// add contribution of each summand
156 for(size_t c = 0; c < m_vpUserData.size(); ++c)
157 {
158 (*m_vpUserData[c])(&vValData[0], vGlobIP, time, si,
159 elem, vCornerCoords, vLocIP, nip, u, vJT);
160 (*m_vpScaleData[c])(&vValScale[0], vGlobIP, time, si,
161 elem, vCornerCoords, vLocIP, nip, u, vJT);
162
163 for(size_t ip = 0; ip < nip; ++ip)
165 mult_add(vValue[ip], vValData[ip], vValScale[ip]);
166 }
167}
168
169template <typename TData, int dim, typename TDataScale, typename TRet>
170template <int refDim>
172eval_and_deriv(TRet vValue[],
173 const MathVector<dim> vGlobIP[],
174 number time, int si,
175 GridObject* elem,
176 const MathVector<dim> vCornerCoords[],
177 const MathVector<refDim> vLocIP[],
178 const size_t nip,
179 LocalVector* u,
180 bool bDeriv,
181 int s,
182 std::vector<std::vector<TRet> > vvvDeriv[],
183 const MathMatrix<refDim, dim>* vJT) const
184{
185// check that size of Scalings and inputs is equal
186 UG_ASSERT(m_vpUserData.size() == m_vpScaleData.size(), "Wrong num Scales.");
187
188// compute value
189 for(size_t ip = 0; ip < nip; ++ip)
190 {
191 // reset value
192 vValue[ip] = 0.0;
193
194 // add contribution of each summand
195 for(size_t c = 0; c < m_vpUserData.size(); ++c)
196 {
198 mult_add(vValue[ip],
199 input_value(c, s, ip),
200 scale_value(c, s, ip));
201 }
202 }
203
204// check if derivative is required
205 if(!bDeriv || this->zero_derivative()) return;
206
207// check sizes
208 UG_ASSERT(m_vpDependData.size() == m_vpScaleDependData.size(),
209 "Wrong num Scales.");
210
211// clear all derivative values
212 this->set_zero(vvvDeriv, nip);
213
214// loop all inputs
215 for(size_t c = 0; c < m_vpUserData.size(); ++c)
216 {
217 // check if input has derivative
218 if(!m_vpUserData[c]->zero_derivative())
219 {
220 for(size_t ip = 0; ip < nip; ++ip)
221 {
222 // loop functions
223 for(size_t fct = 0; fct < input_num_fct(c); ++fct)
224 {
225 // get common fct id for this function
226 const size_t commonFct = input_common_fct(c, fct);
227
228 // loop dofs
229 for(size_t sh = 0; sh < this->num_sh(fct); ++sh)
230 {
232 mult_add(vvvDeriv[ip][commonFct][sh],
233 input_deriv(c, s, ip, fct, sh),
234 scale_value(c, s, ip));
235 }
236 }
237 }
238 }
239
240 // check if scaling has derivative
241 if(!m_vpScaleData[c]->zero_derivative())
242 {
243 for(size_t ip = 0; ip < nip; ++ip)
244 {
245 // loop functions
246 for(size_t fct = 0; fct < scale_num_fct(c); ++fct)
247 {
248 // get common fct id for this function
249 const size_t commonFct = scale_common_fct(c, fct);
250
251 // loop dofs
252 for(size_t sh = 0; sh < this->num_sh(fct); ++sh)
253 {
255 mult_add(vvvDeriv[ip][commonFct][sh],
256 input_value(c, s, ip),
257 scale_deriv(c, s, ip, fct, sh));
258 }
259 }
260 }
261 }
262 }
263}
264
265
266} // end namespace ug
267
268#endif /* __H__UG__LIB_DISC__SPATIAL_DISC__SCALE_ADD_LINKER_IMPL__ */
parameterString s
Definition smart_pointer.h:108
Type based UserData.
Definition user_data.h:501
The base class for all geometric objects, such as vertices, edges, faces, volumes,...
Definition grid_base_objects.h:157
Definition local_algebra.h:198
A class for fixed size, dense matrices.
Definition math_matrix.h:63
a mathematical Vector with N entries.
Definition math_vector.h:97
Definition scale_add_linker.h:61
std::vector< SmartPtr< CplUserData< TData, dim > > > m_vpUserData
data input
Definition scale_add_linker.h:167
void eval_and_deriv(TRet vValue[], const MathVector< dim > vGlobIP[], number time, int si, GridObject *elem, const MathVector< dim > vCornerCoords[], const MathVector< refDim > vLocIP[], const size_t nip, LocalVector *u, bool bDeriv, int s, std::vector< std::vector< TRet > > vvvDeriv[], const MathMatrix< refDim, dim > *vJT=NULL) const
Definition scale_add_linker_impl.h:172
std::vector< SmartPtr< CplUserData< TDataScale, dim > > > m_vpScaleData
data input
Definition scale_add_linker.h:161
void add(SmartPtr< CplUserData< TDataScale, dim > > scale, SmartPtr< CplUserData< TData, dim > > data)
Definition scale_add_linker_impl.h:62
void evaluate(TRet &value, const MathVector< dim > &globIP, number time, int si) const
Definition scale_add_linker_impl.h:114
ScaleAddLinker()
constructor
Definition scale_add_linker.h:68
#define UG_ASSERT(expr, msg)
Definition assert.h:70
#define UG_THROW(msg)
Definition error.h:57
double number
Definition types.h:124
the ug namespace
Linker Traits.
Definition linker_traits.h:47
static void mult_add(TData &out, const TData &in1, const TDataIn &s)
computes out += s * in1 (with appropriate '*')