Reference documentation for deal.II version 8.5.1
tensor_product_manifold.h
1 // ---------------------------------------------------------------------
2 //
3 // Copyright (C) 2016 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 at
12 // the top level of the deal.II distribution.
13 //
14 // ---------------------------------------------------------------------
15 
16 #ifndef dealii__tensor_product_manifold_h
17 #define dealii__tensor_product_manifold_h
18 
19 #include <deal.II/base/config.h>
20 #include <deal.II/base/subscriptor.h>
21 #include <deal.II/base/point.h>
22 #include <deal.II/grid/manifold.h>
23 
24 DEAL_II_NAMESPACE_OPEN
25 
26 
27 
60 template <int dim,
61  int dim_A, int spacedim_A, int chartdim_A,
62  int dim_B, int spacedim_B, int chartdim_B>
64  public ChartManifold<dim,spacedim_A+spacedim_B,chartdim_A+chartdim_B>
65 {
66 public:
71  static const unsigned int chartdim = chartdim_A+chartdim_B;
76  static const unsigned int spacedim = spacedim_A+spacedim_B;
77 
84 
88  virtual
90  pull_back(const Point<spacedim> &space_point) const;
91 
95  virtual
97  push_forward(const Point<chartdim> &chart_point) const;
98 
102  virtual
104  push_forward_gradient(const Point<chartdim> &chart_point) const;
105 
106 private:
109 
112 };
113 
114 
115 
116 /*------------------Template Implementations------------------------*/
117 
118 
119 
120 namespace internal
121 {
122  namespace TensorProductManifold
123  {
124  template <int dim1, int dim2>
125  Tensor<1,dim1+dim2> concat(const Tensor<1,dim1> &p1, const Tensor<1,dim2> &p2)
126  {
128  for (unsigned int d=0; d<dim1; ++d)
129  r[d] = p1[d];
130  for (unsigned int d=0; d<dim2; ++d)
131  r[dim1+d] = p2[d];
132  return r;
133  }
134 
135  template <int dim1, int dim2>
136  Point<dim1+dim2> concat(const Point<dim1> &p1, const Point<dim2> &p2)
137  {
139  for (unsigned int d=0; d<dim1; ++d)
140  r[d] = p1[d];
141  for (unsigned int d=0; d<dim2; ++d)
142  r[dim1+d] = p2[d];
143  return r;
144  }
145 
146  template <int dim1, int dim2>
147  void split_point(const Point<dim1+dim2> &source, Point<dim1> &p1, Point<dim2> &p2)
148  {
149  for (unsigned int d=0; d<dim1; ++d)
150  p1[d] = source[d];
151  for (unsigned int d=0; d<dim2; ++d)
152  p2[d] = source[dim1+d];
153  }
154 
155  }
156 }
157 
158 template <int dim,
159  int dim_A, int spacedim_A, int chartdim_A,
160  int dim_B, int spacedim_B, int chartdim_B>
165  : ChartManifold<dim,spacedim_A+spacedim_B,chartdim_A+chartdim_B> (
167  manifold_A.get_periodicity(),
168  manifold_B.get_periodicity())),
169  manifold_A (&manifold_A),
170  manifold_B (&manifold_B)
171 {}
172 
173 template <int dim,
174  int dim_A, int spacedim_A, int chartdim_A,
175  int dim_B, int spacedim_B, int chartdim_B>
179 {
180  Point<spacedim_A> space_point_A;
181  Point<spacedim_B> space_point_B;
182  internal::TensorProductManifold::split_point(space_point, space_point_A, space_point_B);
183 
184  Point<chartdim_A> result_A = manifold_A->pull_back(space_point_A);
185  Point<chartdim_B> result_B = manifold_B->pull_back(space_point_B);
186 
187  return internal::TensorProductManifold::concat(result_A, result_B);
188 }
189 
190 template <int dim,
191  int dim_A, int spacedim_A, int chartdim_A,
192  int dim_B, int spacedim_B, int chartdim_B>
196 {
197  Point<chartdim_A> chart_point_A;
198  Point<chartdim_B> chart_point_B;
199  internal::TensorProductManifold::split_point(chart_point, chart_point_A, chart_point_B);
200 
201  Point<spacedim_A> result_A = manifold_A->push_forward(chart_point_A);
202  Point<spacedim_B> result_B = manifold_B->push_forward(chart_point_B);
203 
204  return internal::TensorProductManifold::concat(result_A, result_B);
205 }
206 
207 template <int dim,
208  int dim_A, int spacedim_A, int chartdim_A,
209  int dim_B, int spacedim_B, int chartdim_B>
213 
216 {
217  Point<chartdim_A> chart_point_A;
218  Point<chartdim_B> chart_point_B;
219  internal::TensorProductManifold::split_point(chart_point, chart_point_A, chart_point_B);
220 
222  = manifold_A->push_forward_gradient(chart_point_A);
224  = manifold_B->push_forward_gradient(chart_point_B);
225 
226 
228  for (unsigned int i = 0; i<chartdim_A; ++i)
229  for (unsigned int j = 0; j<spacedim_A; ++j)
230  result[j][i] = result_A[j][i];
231  for (unsigned int i = 0; i<chartdim_B; ++i)
232  for (unsigned int j = 0; j<spacedim_B; ++j)
233  result[j+spacedim_A][i+chartdim_A] = result_B[j][i];
234 
235  return result;
236 }
237 
238 
239 
240 
241 DEAL_II_NAMESPACE_CLOSE
242 
243 #endif
static const unsigned int chartdim
virtual Point< chartdim > pull_back(const Point< spacedim > &space_point) const
Definition: point.h:89
Tensor product manifold of two ChartManifolds.
virtual DerivativeForm< 1, chartdim, spacedim > push_forward_gradient(const Point< chartdim > &chart_point) const
SymmetricTensor< 2, dim, Number > d(const Tensor< 2, dim, Number > &F, const Tensor< 2, dim, Number > &dF_dt)
virtual Point< spacedim > push_forward(const Point< chartdim > &chart_point) const
static const unsigned int spacedim
Definition: mpi.h:41
TensorProductManifold(const ChartManifold< dim_A, spacedim_A, chartdim_A > &manifold_A, const ChartManifold< dim_B, spacedim_B, chartdim_B > &manifold_B)