Reference documentation for deal.II version 9.1.1
\(\newcommand{\dealcoloneq}{\mathrel{\vcenter{:}}=}\)
derivative_form.h
1 // ---------------------------------------------------------------------
2 //
3 // Copyright (C) 2013 - 2019 by the deal.II authors
4 //
5 // This file is part of the deal.II library.
6 //
7 // The deal.II library is free software; you can use it, redistribute
8 // it, and/or modify it under the terms of the GNU Lesser General
9 // Public License as published by the Free Software Foundation; either
10 // version 2.1 of the License, or (at your option) any later version.
11 // The full text of the license can be found in the file LICENSE.md at
12 // the top level directory of deal.II.
13 //
14 // ---------------------------------------------------------------------
15 
16 #ifndef dealii_derivative_form_h
17 #define dealii_derivative_form_h
18 
19 #include <deal.II/base/tensor.h>
20 
21 DEAL_II_NAMESPACE_OPEN
22 
57 template <int order, int dim, int spacedim, typename Number = double>
59 {
60 public:
64  DerivativeForm() = default;
65 
70 
74  Tensor<order, dim, Number> &operator[](const unsigned int i);
75 
79  const Tensor<order, dim, Number> &operator[](const unsigned int i) const;
80 
86 
92 
98  operator Tensor<order + 1, dim, Number>() const;
99 
103  operator Tensor<1, dim, Number>() const;
104 
110  transpose() const;
111 
118  norm() const;
119 
125  Number
126  determinant() const;
127 
138  covariant_form() const;
139 
144  static std::size_t
146 
151  int,
152  << "Invalid DerivativeForm index " << arg1);
153 
154 private:
160  times_T_t(const Tensor<2, dim, Number> &T) const;
161 
162 
167 };
168 
169 
170 /*--------------------------- Inline functions -----------------------------*/
171 
172 #ifndef DOXYGEN
173 
174 template <int order, int dim, int spacedim, typename Number>
177 {
178  Assert((dim == spacedim),
179  ExcMessage("Only allowed for forms with dim==spacedim."));
180  if (dim == spacedim)
181  for (unsigned int j = 0; j < dim; ++j)
182  (*this)[j] = T[j];
183 }
184 
185 
186 
187 template <int order, int dim, int spacedim, typename Number>
191 {
192  Assert((dim == spacedim), ExcMessage("Only allowed when dim==spacedim."));
193 
194  if (dim == spacedim)
195  for (unsigned int j = 0; j < dim; ++j)
196  (*this)[j] = ta[j];
197  return *this;
198 }
199 
200 
201 
202 template <int order, int dim, int spacedim, typename Number>
206 {
207  Assert((1 == spacedim) && (order == 1),
208  ExcMessage("Only allowed for spacedim==1 and order==1."));
209 
210  (*this)[0] = T;
211 
212  return *this;
213 }
214 
215 
216 
217 template <int order, int dim, int spacedim, typename Number>
220 {
221  Assert(i < spacedim, ExcIndexRange(i, 0, spacedim));
222 
223  return tensor[i];
224 }
225 
226 
227 
228 template <int order, int dim, int spacedim, typename Number>
229 inline const Tensor<order, dim, Number> &
231  operator[](const unsigned int i) const
232 {
233  Assert(i < spacedim, ExcIndexRange(i, 0, spacedim));
234 
235  return tensor[i];
236 }
237 
238 
239 
240 template <int order, int dim, int spacedim, typename Number>
242 operator Tensor<1, dim, Number>() const
243 {
244  Assert((1 == spacedim) && (order == 1),
245  ExcMessage("Only allowed for spacedim==1."));
246 
247  return (*this)[0];
248 }
249 
250 
251 
252 template <int order, int dim, int spacedim, typename Number>
254 operator Tensor<order + 1, dim, Number>() const
255 {
256  Assert((dim == spacedim), ExcMessage("Only allowed when dim==spacedim."));
257 
259 
260  if (dim == spacedim)
261  for (unsigned int j = 0; j < dim; ++j)
262  t[j] = (*this)[j];
263 
264  return t;
265 }
266 
267 
268 
269 template <int order, int dim, int spacedim, typename Number>
272 {
273  Assert(order == 1, ExcMessage("Only for rectangular DerivativeForm."));
275 
276  for (unsigned int i = 0; i < spacedim; ++i)
277  for (unsigned int j = 0; j < dim; ++j)
278  tt[j][i] = (*this)[i][j];
279 
280  return tt;
281 }
282 
283 
284 
285 template <int order, int dim, int spacedim, typename Number>
288  const Tensor<2, dim, Number> &T) const
289 {
290  Assert(order == 1, ExcMessage("Only for order == 1."));
292  for (unsigned int i = 0; i < spacedim; ++i)
293  for (unsigned int j = 0; j < dim; ++j)
294  dest[i][j] = (*this)[i] * T[j];
295 
296  return dest;
297 }
298 
299 
300 
301 template <int order, int dim, int spacedim, typename Number>
304 {
305  typename numbers::NumberTraits<Number>::real_type sum_of_squares = 0;
306  for (unsigned int i = 0; i < spacedim; ++i)
307  sum_of_squares += tensor[i].norm_square();
308  return std::sqrt(sum_of_squares);
309 }
310 
311 
312 
313 template <int order, int dim, int spacedim, typename Number>
314 inline Number
316 {
317  Assert(order == 1, ExcMessage("Only for order == 1."));
318  if (dim == spacedim)
319  {
320  const Tensor<2, dim, Number> T =
321  static_cast<Tensor<2, dim, Number>>(*this);
323  }
324  else
325  {
326  Assert(spacedim > dim, ExcMessage("Only for spacedim>dim."));
328  Tensor<2, dim, Number> G; // First fundamental form
329  for (unsigned int i = 0; i < dim; ++i)
330  for (unsigned int j = 0; j < dim; ++j)
331  G[i][j] = DF_t[i] * DF_t[j];
332 
333  return (std::sqrt(::determinant(G)));
334  }
335 }
336 
337 
338 
339 template <int order, int dim, int spacedim, typename Number>
342 {
343  if (dim == spacedim)
344  {
345  const Tensor<2, dim, Number> DF_t =
346  ::transpose(invert(static_cast<Tensor<2, dim, Number>>(*this)));
348  }
349  else
350  {
351  const DerivativeForm<1, spacedim, dim> DF_t = this->transpose();
352  Tensor<2, dim, Number> G; // First fundamental form
353  for (unsigned int i = 0; i < dim; ++i)
354  for (unsigned int j = 0; j < dim; ++j)
355  G[i][j] = DF_t[i] * DF_t[j];
356 
357  return (this->times_T_t(invert(G)));
358  }
359 }
360 
361 
362 template <int order, int dim, int spacedim, typename Number>
363 inline std::size_t
365 {
367 }
368 
369 #endif // DOXYGEN
370 
371 
372 
395 template <int spacedim, int dim, typename Number>
398  const Tensor<1, dim, Number> & d_x)
399 {
401  for (unsigned int i = 0; i < spacedim; ++i)
402  dest[i] = grad_F[i] * d_x;
403  return dest;
404 }
405 
406 
407 
416 // rank=2
417 template <int spacedim, int dim, typename Number>
420  const Tensor<2, dim, Number> & D_X)
421 {
423  for (unsigned int i = 0; i < dim; ++i)
424  dest[i] = apply_transformation(grad_F, D_X[i]);
425 
426  return dest;
427 }
428 
445 template <int spacedim, int dim, typename Number>
449 {
451 
452  for (unsigned int i = 0; i < spacedim; ++i)
453  dest[i] = apply_transformation(DF1, DF2[i]);
454 
455  return dest;
456 }
457 
458 
466 template <int dim, int spacedim, typename Number>
469 {
471  tt = DF.transpose();
472  return tt;
473 }
474 
475 
476 DEAL_II_NAMESPACE_CLOSE
477 
478 #endif
Number determinant(const SymmetricTensor< 2, dim, Number > &)
SymmetricTensor< 2, dim, Number > invert(const SymmetricTensor< 2, dim, Number > &t)
DerivativeForm & operator=(const Tensor< order+1, dim, Number > &)
static ::ExceptionBase & ExcIndexRange(int arg1, int arg2, int arg3)
Number determinant() const
Tensor< order, dim, Number > tensor[spacedim]
static ::ExceptionBase & ExcMessage(std::string arg1)
#define DeclException1(Exception1, type1, outsequence)
Definition: exceptions.h:518
DerivativeForm< 1, dim, spacedim, Number > times_T_t(const Tensor< 2, dim, Number > &T) const
#define Assert(cond, exc)
Definition: exceptions.h:1407
Tensor< 2, spacedim, Number > apply_transformation(const DerivativeForm< 1, dim, spacedim, Number > &DF1, const DerivativeForm< 1, dim, spacedim, Number > &DF2)
DerivativeForm()=default
DerivativeForm< 1, spacedim, dim, Number > transpose() const
static std::size_t memory_consumption()
numbers::NumberTraits< Number >::real_type norm() const
Tensor< 1, spacedim, Number > apply_transformation(const DerivativeForm< 1, dim, spacedim, Number > &grad_F, const Tensor< 1, dim, Number > &d_x)
Number determinant(const SymmetricTensor< 2, dim, Number > &t)
DerivativeForm< 1, dim, spacedim, Number > covariant_form() const
Definition: mpi.h:90
static ::ExceptionBase & ExcInvalidTensorIndex(int arg1)
DerivativeForm< 1, spacedim, dim, Number > transpose(const DerivativeForm< 1, dim, spacedim, Number > &DF)
Tensor< order, dim, Number > & operator[](const unsigned int i)
DerivativeForm< 1, spacedim, dim > apply_transformation(const DerivativeForm< 1, dim, spacedim, Number > &grad_F, const Tensor< 2, dim, Number > &D_X)