dune-geometry 2.9.1
Loading...
Searching...
No Matches
hcube.cc
Go to the documentation of this file.
1// -*- tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*-
2// vi: set et ts=4 sw=2 sts=2:
3// SPDX-FileCopyrightInfo: Copyright (C) DUNE Project contributors, see file LICENSE.md in module root
4// SPDX-License-Identifier: LicenseRef-GPL-2.0-only-with-DUNE-exception
5#ifndef DUNE_GEOMETRY_REFINEMENT_HCUBE_CC
6#define DUNE_GEOMETRY_REFINEMENT_HCUBE_CC
7
42#include <cassert>
43
44#include <dune/common/fvector.hh>
45#include <dune/common/iteratorfacades.hh>
46
49
50#include "base.cc" // for RefinementTraits
51
52namespace Dune
53{
54 namespace RefinementImp
55 {
62 namespace HCube
63 {
73 template<int dimension_, class CoordType>
75 {
76 public:
78 constexpr static int dimension = dimension_;
79 //- Know yourself
81
82 template<int codimension>
83 struct Codim;
85 typedef FieldVector<CoordType, dimension> CoordVector;
87 typedef FieldVector<int, (1<<dimension)> IndexVector;
88
89 static unsigned nVertices(unsigned nIntervals);
90 static VertexIterator vBegin(unsigned nIntervals);
91 static VertexIterator vEnd(unsigned nIntervals);
92
93 static unsigned nElements(unsigned nIntervals);
94 static ElementIterator eBegin(unsigned nIntervals);
95 static ElementIterator eEnd(unsigned nIntervals);
96 };
97
98 template<int dimension, class CoordType>
99 template<int codimension>
100 struct RefinementImp<dimension, CoordType>::Codim
101 {
102 class SubEntityIterator;
104 };
105
106 template<int dimension, class CoordType>
107 unsigned
109 nVertices(unsigned nIntervals)
110 {
111 // return (nIntervals + 1)^dim
112 return Dune::power(nIntervals+1u, unsigned(dimension));
113 }
114
115 template<int dimension, class CoordType>
118 vBegin(unsigned nIntervals)
119 {
120 return VertexIterator(0,nIntervals);
121 }
122
123 template<int dimension, class CoordType>
126 vEnd(unsigned nIntervals)
127 {
128 return VertexIterator(nVertices(nIntervals),nIntervals);
129 }
130
131 template<int dimension, class CoordType>
132 unsigned
134 nElements(unsigned nIntervals)
135 {
136 static_assert(dimension >= 0,
137 "Negative dimension given, what the heck is that supposed to mean?");
138 // return nIntervals^dim
139 return Dune::power(nIntervals, unsigned(dimension));
140 }
141
142 template<int dimension, class CoordType>
145 eBegin(unsigned nIntervals)
146 {
147 return ElementIterator(0,nIntervals);
148 }
149
150 template<int dimension, class CoordType>
153 eEnd(unsigned nIntervals)
154 {
155 return ElementIterator(nElements(nIntervals),nIntervals);
156 }
157
158 //
159 // The iterators
160 //
161
162#ifdef DOXYGEN
174 template<int dimension, class CoordType, int codimension>
176#else
177 template<int dimension, class CoordType, int codimension>
179#endif //DOXYGEN
180
181 // for vertices
182
183 template<int dimension, class CoordType>
184 class RefinementSubEntityIteratorSpecial<dimension, CoordType, dimension>
185 {
186 public:
188 typedef typename Refinement::template Codim<dimension>::SubEntityIterator Common;
190
191 CoordVector coords() const;
192
193 private:
194 const Common & asCommon() const
195 {
196 return *static_cast<const Common*>(this);
197 }
198 };
199
200 template<int dimension, class CoordType>
201 typename RefinementSubEntityIteratorSpecial<dimension, CoordType, dimension>::CoordVector
203 coords() const
204 {
205 std::array<unsigned int, dimension> v(asCommon().vertexCoord());
206 CoordVector c;
207 for (int d = 0; d < dimension; d++)
208 {
209 c[d] = v[d]*1.0 / asCommon()._nIntervals;
210 }
211 return c;
212 }
213
214 // for elements
215
216 template<int dimension, class CoordType>
217 class RefinementSubEntityIteratorSpecial<dimension, CoordType, 0>
218 {
219 public:
221 typedef typename Refinement::template Codim<0>::SubEntityIterator Common;
224
225 IndexVector vertexIndices() const;
226 CoordVector coords() const;
227
228 private:
229 const Common & asCommon() const
230 {
231 return *static_cast<const Common*>(this);
232 }
233 };
234
235 template<int dimension, class CoordType>
236 typename RefinementSubEntityIteratorSpecial<dimension, CoordType, 0>::IndexVector
238 vertexIndices() const
239 {
240 constexpr static int nIndices = 1 << dimension;
241
242 // cell index tuple
243 std::array<unsigned int, dimension> e(asCommon().cellCoord());
244
245 // vertices
246 IndexVector vec;
247 for(int i = 0; i < nIndices; ++i)
248 {
249 int base = 1;
250 std::array<unsigned int, dimension> alpha(asCommon().idx2multiidx(i));
251 for (int d = 0; d < dimension; d++) {
252 vec[i] += (alpha[d] + e[d]) * base;
253 base *= asCommon()._nIntervals+1;
254 }
255 }
256 return vec;
257 }
258
259 template<int dimension, class CoordType>
262 coords() const
263 {
264 std::array<unsigned int, dimension> v(asCommon().cellCoord());
265 CoordVector c;
266 for (int d=0; d<dimension; d++)
267 {
268 c[d] = (v[d]*1.0 + 0.5) / asCommon()._nIntervals;
269 }
270 return c;
271 }
272
273 // common
274 template<int dimension, class CoordType>
275 template<int codimension>
276 class RefinementImp<dimension, CoordType>::Codim<codimension>::SubEntityIterator
277 : public ForwardIteratorFacade<typename RefinementImp<dimension,
278 CoordType>::template Codim<codimension>::SubEntityIterator, int>,
279 public RefinementSubEntityIteratorSpecial<dimension, CoordType, codimension>
280 {
281 public:
283 typedef typename Refinement::template Codim<codimension>::SubEntityIterator This;
284
285 SubEntityIterator(unsigned int index, unsigned int nIntervals);
286
287 bool equals(const This &other) const;
288 void increment();
289
290 int index() const;
291 Geometry geometry () const;
292 private:
293 friend class RefinementSubEntityIteratorSpecial<dimension, CoordType, codimension>;
294 unsigned int _index;
295 unsigned int _nIntervals;
296
297 std::array<unsigned int, dimension>
298 cellCoord(unsigned int idx) const
299 {
300 return idx2coord(idx, _nIntervals);
301 }
302
303 std::array<unsigned int, dimension>
304 vertexCoord(unsigned int idx) const
305 {
306 return idx2coord(idx, _nIntervals+1u);
307 }
308
309 std::array<unsigned int, dimension>
310 cellCoord() const
311 {
312 return cellCoord(_index);
313 }
314
315 std::array<unsigned int, dimension>
316 vertexCoord() const
317 {
318 return vertexCoord(_index);
319 }
320
321 std::array<unsigned int, dimension>
322 idx2coord(unsigned int idx, unsigned int w) const
323 {
324 std::array<unsigned int, dimension> c;
325 for (unsigned int d = 0; d < dimension; d++)
326 {
327 c[d] = idx%w;
328 idx = idx/w;
329 }
330 return c;
331 }
332
333 unsigned int
334 coord2idx(std::array<unsigned int, dimension> c, unsigned int w) const
335 {
336 unsigned int i = 0;
337 for (unsigned int d = dimension; d > 0; d--)
338 {
339 i *= w;
340 i += c[d-1];
341 }
342 return i;
343 }
344
345 std::array<unsigned int, dimension>
346 idx2multiidx(unsigned int idx) const
347 {
348 std::array<unsigned int, dimension> alpha;
349 for (unsigned int i = 0; i < dimension; ++i)
350 alpha[i] = (idx >> i) & 1u;
351 return alpha;
352 }
353 };
354
355#ifndef DOXYGEN
356 template<int dimension, class CoordType>
357 template<int codimension>
358 RefinementImp<dimension, CoordType>::Codim<codimension>::SubEntityIterator::
359 SubEntityIterator(unsigned int index, unsigned int nIntervals)
360 : _index(index), _nIntervals(nIntervals)
361 {}
362
363 template<int dimension, class CoordType>
364 template<int codimension>
365 bool
366 RefinementImp<dimension, CoordType>::Codim<codimension>::SubEntityIterator::
367 equals(const This &other) const
368 {
369 return ((_index == other._index) && (_nIntervals == other._nIntervals));
370 }
371
372 template<int dimension, class CoordType>
373 template<int codimension>
374 void
375 RefinementImp<dimension, CoordType>::Codim<codimension>::SubEntityIterator::
376 increment()
377 {
378 ++_index;
379 }
380
381 template<int dimension, class CoordType>
382 template<int codimension>
383 int
384 RefinementImp<dimension, CoordType>::Codim<codimension>::SubEntityIterator::
385 index() const
386 {
387 return _index;
388 }
389
390 template<int dimension, class CoordType>
391 template<int codimension>
392 typename RefinementImp<dimension, CoordType>::template Codim<codimension>::Geometry
393 RefinementImp<dimension, CoordType>::Codim<codimension>::SubEntityIterator::geometry () const
394 {
395 std::array<unsigned int,dimension> intCoords = idx2coord(_index,_nIntervals);
396
397 Dune::FieldVector<CoordType,dimension> lower;
398 Dune::FieldVector<CoordType,dimension> upper;
399
400 assert(codimension == 0 or codimension == dimension);
401
402 if constexpr (codimension == 0) {
403 for (size_t j = 0; j < dimension; j++)
404 {
405 lower[j] = double(intCoords[j]) / double(_nIntervals);
406 upper[j] = double(intCoords[j] + 1) / double(_nIntervals);
407 }
408
409 return typename RefinementImp<dimension,
410 CoordType>::template Codim<codimension>::Geometry(lower,upper);
411 } else {
412 for (size_t j = 0; j < dimension; j++)
413 lower[j] = upper[j] = double(intCoords[j]) / double(_nIntervals);
414
415 return typename RefinementImp<dimension,
416 CoordType>::template Codim<codimension>::Geometry(lower,upper,std::bitset<dimension>(0));
417 }
418 }
419
420#endif // DOXYGEN
421
422 } // namespace HCube
423
424 // ///////////////////////
425 //
426 // The refinement traits
427 //
428
429#ifndef DOXYGEN
430 template<unsigned topologyId, class CoordType, unsigned coerceToId,
431 int dim>
432 struct Traits<
433 topologyId, CoordType, coerceToId, dim,
434 typename std::enable_if<
435 (dim >= 2 &&
436 (GeometryTypes::cube(dim).id() >> 1) ==
437 (topologyId >> 1) &&
438 (GeometryTypes::cube(dim).id() >> 1) ==
439 (coerceToId >> 1)
440 )>::type
441 >
442 {
443 typedef HCube::RefinementImp<dim, CoordType> Imp;
444 };
445#endif
446
447 } // namespace RefinementImp
448
449} // namespace Dune
450
451#endif // DUNE_GEOMETRY_REFINEMENT_HCUBE_CC
This file contains the parts independent of a particular Refinement implementation.
A geometry implementation for axis-aligned hypercubes.
Definition affinegeometry.hh:21
A geometry implementation for axis-aligned hypercubes.
Definition axisalignedcubegeometry.hh:50
Static tag representing a codimension.
Definition dimension.hh:24
Refinement implementation for hypercubes
Definition hcube.cc:75
Codim< 0 >::SubEntityIterator ElementIterator
Definition hcube.cc:86
static ElementIterator eEnd(unsigned nIntervals)
Definition hcube.cc:153
static unsigned nVertices(unsigned nIntervals)
Definition hcube.cc:109
static VertexIterator vEnd(unsigned nIntervals)
Definition hcube.cc:126
FieldVector< int,(1<< dimension)> IndexVector
Definition hcube.cc:87
Codim< dimension >::SubEntityIterator VertexIterator
Definition hcube.cc:84
FieldVector< CoordType, dimension > CoordVector
Definition hcube.cc:85
static unsigned nElements(unsigned nIntervals)
Definition hcube.cc:134
RefinementImp< dimension, CoordType > Refinement
Definition hcube.cc:80
static ElementIterator eBegin(unsigned nIntervals)
Definition hcube.cc:145
static constexpr int dimension
Know your own dimension.
Definition hcube.cc:78
static VertexIterator vBegin(unsigned nIntervals)
Definition hcube.cc:118
Dune::AxisAlignedCubeGeometry< CoordType, dimension-codimension, dimension > Geometry
Definition hcube.cc:103
SubEntityIterator base class for hypercube refinement.
Definition hcube.cc:175
Refinement::template Codim< dimension >::SubEntityIterator Common
Definition hcube.cc:188
RefinementImp< dimension, CoordType > Refinement
Definition hcube.cc:220
Refinement::template Codim< 0 >::SubEntityIterator Common
Definition hcube.cc:221
SubEntityIterator(unsigned int index, unsigned int nIntervals)
RefinementImp< dimension, CoordType > Refinement
Definition hcube.cc:282
Refinement::template Codim< codimension >::SubEntityIterator This
Definition hcube.cc:283