dune-grid 2.10
Loading...
Searching...
No Matches
albertagrid.cc
Go to the documentation of this file.
1// SPDX-FileCopyrightText: Copyright © DUNE Project contributors, see file LICENSE.md in module root
2// SPDX-License-Identifier: LicenseRef-GPL-2.0-only-with-DUNE-exception
3// -*- tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*-
4// vi: set et ts=4 sw=2 sts=2:
5#ifndef DUNE_ALBERTAGRID_CC
6#define DUNE_ALBERTAGRID_CC
7
8//************************************************************************
9//
10// implementation of AlbertaGrid
11//
12// namespace Dune
13//
14//************************************************************************
15#include "geometry.cc"
16#include "entity.cc"
17#include "intersection.cc"
18
19namespace Dune
20{
21
22 namespace Alberta
23 {
25 }
26
27
28 template< int dim, int dimworld >
30 {
31 // If this check fails, define ALBERTA_DIM accordingly
32 static_assert((dimworld == Alberta::dimWorld),
33 "Template Parameter dimworld does not match "
34 "ALBERTA's DIM_OF_WORLD setting.");
35 }
36
37
38 // AlbertaGrid
39 // -----------
40
41 template< int dim, int dimworld >
43 : mesh_(),
44 maxlevel_( 0 ),
45 numBoundarySegments_( 0 ),
46 hIndexSet_( dofNumbering_ ),
47 idSet_( hIndexSet_ ),
48 levelIndexVec_( (size_t)MAXL, 0 ),
49 leafIndexSet_( 0 ),
50 sizeCache_( *this ),
51 leafMarkerVector_( dofNumbering_ ),
52 levelMarkerVector_( (size_t)MAXL, MarkerVector( dofNumbering_ ) )
53 {
55 }
56
57
58 template< int dim, int dimworld >
59 template< class Proj, class Impl >
63 : mesh_(),
64 maxlevel_( 0 ),
65 numBoundarySegments_( 0 ),
66 hIndexSet_( dofNumbering_ ),
67 idSet_( hIndexSet_ ),
68 levelIndexVec_( (size_t)MAXL, 0 ),
69 leafIndexSet_ ( 0 ),
70 sizeCache_( *this ),
71 leafMarkerVector_( dofNumbering_ ),
72 levelMarkerVector_( (size_t)MAXL, MarkerVector( dofNumbering_ ) )
73 {
75
76 numBoundarySegments_ = mesh_.create( macroData, projectionFactory );
77 if( !mesh_ )
78 DUNE_THROW( AlbertaError, "Invalid macro data structure." );
79
80 setup();
81 hIndexSet_.create();
82
83 calcExtras();
84 }
85
86
87 template< int dim, int dimworld >
90 const std::shared_ptr< DuneBoundaryProjection< dimensionworld > > &projection )
91 : mesh_(),
92 maxlevel_( 0 ),
93 numBoundarySegments_( 0 ),
94 hIndexSet_( dofNumbering_ ),
95 idSet_( hIndexSet_ ),
96 levelIndexVec_( (size_t)MAXL, 0 ),
97 leafIndexSet_ ( 0 ),
98 sizeCache_( *this ),
99 leafMarkerVector_( dofNumbering_ ),
100 levelMarkerVector_( (size_t)MAXL, MarkerVector( dofNumbering_ ) )
101 {
103
104 if( projection != 0 )
105 {
106 Alberta::DuneGlobalBoundaryProjectionFactory< dimension > projectionFactory( projection );
107 numBoundarySegments_ = mesh_.create( macroData, projectionFactory );
108 }
109 else
110 numBoundarySegments_ = mesh_.create( macroData );
111 if( !mesh_ )
112 DUNE_THROW( AlbertaError, "Invalid macro data structure." );
113
114 setup();
115 hIndexSet_.create();
116
117 calcExtras();
118 }
119
120
121 template < int dim, int dimworld >
123 ::AlbertaGrid ( const std::string &macroGridFileName )
124 : mesh_(),
125 maxlevel_( 0 ),
126 hIndexSet_( dofNumbering_ ),
127 idSet_( hIndexSet_ ),
128 levelIndexVec_( (size_t)MAXL, 0 ),
129 leafIndexSet_ ( 0 ),
130 sizeCache_( *this ),
131 leafMarkerVector_( dofNumbering_ ),
132 levelMarkerVector_( (size_t)MAXL, MarkerVector( dofNumbering_ ) )
133 {
135
136 numBoundarySegments_ = mesh_.create( macroGridFileName );
137 if( !mesh_ )
138 {
140 "Grid file '" << macroGridFileName
141 << "' is not in ALBERTA macro triangulation format." );
142 }
143
144 setup();
145 hIndexSet_.create();
146
147 calcExtras();
148
149 std::cout << typeName() << " created from macro grid file '"
150 << macroGridFileName << "'." << std::endl;
151 }
152
153
154 template< int dim, int dimworld >
156 {
157 dofNumbering_.create( mesh_ );
158
159 levelProvider_.create( dofNumbering_ );
160
161#if DUNE_ALBERTA_CACHE_COORDINATES
162 coordCache_.create( dofNumbering_ );
163#endif
164 }
165
166
167 template< int dim, int dimworld >
168 inline void AlbertaGrid< dim, dimworld >::removeMesh ()
169 {
170 for( size_t i = 0; i < levelIndexVec_.size(); ++i )
171 {
172 if( levelIndexVec_[ i ] != 0 )
173 delete levelIndexVec_[ i ];
174 levelIndexVec_[ i ] = 0;
175 }
176
177 if( leafIndexSet_ != 0 )
178 delete leafIndexSet_;
179 leafIndexSet_ = 0;
180
181 // release dof vectors
182 hIndexSet_.release();
183 levelProvider_.release();
184#if DUNE_ALBERTA_CACHE_COORDINATES
185 coordCache_.release();
186#endif
187 dofNumbering_.release();
188
189 sizeCache_.reset();
190
191 mesh_.release();
192 }
193
194
195 template< int dim, int dimworld >
197 {
198 removeMesh();
199 }
200
201
202 template< int dim, int dimworld >
203 template< int codim, PartitionIteratorType pitype >
205 ::template Codim< codim >::template Partition<pitype>::LevelIterator
207 {
209 assert( level >= 0 );
210
211 if( level > maxlevel_ )
212 return lend< codim, pitype >( level );
213 MarkerVector &markerVector = levelMarkerVector_[ level ];
214
215 if( (codim > 0) && !markerVector.up2Date() )
216 markerVector.template markSubEntities< 1 >( lbegin< 0 >( level ), lend< 0 >( level ) );
217
218 return LevelIteratorImp( *this, &markerVector, level );
219 }
220
221
222 template< int dim, int dimworld >
223 template< int codim, PartitionIteratorType pitype >
225 ::template Codim< codim >::template Partition< pitype >::LevelIterator
227 {
229 assert( level >= 0 );
230
231 return LevelIteratorImp( *this, level );
232 }
233
234
235 template< int dim, int dimworld >
236 template< int codim >
238 ::template Codim< codim >::LevelIterator
240 {
241 return lbegin< codim, All_Partition >( level );
242 }
243
244
245 template< int dim, int dimworld >
246 template< int codim >
248 ::template Codim< codim >::LevelIterator
250 {
251 return lend< codim, All_Partition >( level );
252 }
253
254
255 template< int dim, int dimworld >
256 template< int codim, PartitionIteratorType pitype >
258 ::template Codim< codim >::template Partition< pitype >::LeafIterator
260 {
262
263 MarkerVector &markerVector = leafMarkerVector_;
264 const int firstMarkedCodim = 2;
265 if( (codim >= firstMarkedCodim) && !markerVector.up2Date() )
267
268 return LeafIteratorImp( *this, &markerVector, maxlevel_ );
269 }
270
272 template< int dim, int dimworld >
273 template< int codim, PartitionIteratorType pitype >
275 ::template Codim< codim >::template Partition< pitype >::LeafIterator
277 {
279 return LeafIteratorImp( *this, maxlevel_ );
280 }
281
282
283 template< int dim, int dimworld >
284 template< int codim >
291
292
293 template< int dim, int dimworld >
294 template< int codim >
296 ::template Codim< codim >::LeafIterator
301
302
303 template< int dim, int dimworld >
305 {
306 typedef typename Traits::template Codim< 0 >::LeafIterator LeafIterator;
307
308 // only MAXL levels allowed
309 assert( (refCount >= 0) && (refCount + maxlevel_ < MAXL) );
310
311 for( int i = 0; i < refCount; ++i )
312 {
313 // mark all interior elements
314 const LeafIterator endit = leafend< 0 >();
315 for( LeafIterator it = leafbegin< 0 >(); it != endit; ++it )
316 mark( 1, *it );
317
318 preAdapt();
319 adapt();
320 postAdapt();
321 }
322 }
323
324
325 template< int dim, int dimworld >
326 template< class DataHandle >
329 {
330 typedef typename Traits::template Codim< 0 >::LeafIterator LeafIterator;
331
332 // only MAXL levels allowed
333 assert( (refCount >= 0) && (refCount + maxlevel_ < MAXL) );
334
335 for( int i = 0; i < refCount; ++i )
336 {
337 // mark all interior elements
338 const LeafIterator endit = leafend< 0 >();
339 for( LeafIterator it = leafbegin< 0 >(); it != endit; ++it )
340 mark( 1, *it );
342 adapt( handle );
343 }
345
346
347 template< int dim, int dimworld >
349 {
350 adaptationState_.preAdapt();
351 return adaptationState_.coarsen();
352 }
353
354
355 template < int dim, int dimworld >
357 {
358#ifndef NDEBUG
359 if( leafIndexSet_ != 0 )
360 {
361 bool consistent = true;
362 for( int codim = 0; codim <= dimension; ++codim )
363 {
364 if( int(leafIndexSet_->size( codim )) == mesh_.size( codim ) )
365 continue;
366 std::cerr << "Incorrect size of leaf index set for codimension "
367 << codim << "!" << std::endl;
368 std::cerr << "DUNE index set reports: " << leafIndexSet_->size( codim )
369 << std::endl;
370 std::cerr << "ALBERTA mesh reports: " << mesh_.size( codim ) << std::endl;
371 consistent = false;
372 }
373 if( !consistent )
374 abort();
375 }
376#endif
377
378 levelProvider_.markAllOld();
379 adaptationState_.postAdapt();
380 }
381
383 template< int dim, int dimworld >
385 ::mark( int refCount, const typename Traits::template Codim< 0 >::Entity &e )
386 {
387 // if not leaf entity, leave method
388 if( !e.isLeaf() )
389 return false;
390
391 // don't mark macro elements for coarsening
392 if( refCount < -e.level() )
393 return false;
394
395 // take back previous marking
396 adaptationState_.unmark( getMark( e ) );
397
398 // set new marking
399 adaptationState_.mark( refCount );
400 e.impl().elementInfo().setMark( refCount );
402 return true;
403 }
404
405
406 template< int dim, int dimworld >
409 {
410 return e.impl().elementInfo().getMark();
411 }
412
413
414 template< int dim, int dimworld >
416 {
417 // this is already done in postAdapt
418 //levelProvider_.markAllOld();
419
420 // adapt mesh
421 hIndexSet_.preAdapt();
422 const bool refined = mesh_.refine();
423 const bool coarsened = (adaptationState_.coarsen() ? mesh_.coarsen() : false);
424 adaptationState_.adapt();
425 hIndexSet_.postAdapt();
426
427 if( refined || coarsened )
428 calcExtras();
429
430 // return true if elements were created
431 return refined;
432 }
434
435 template< int dim, int dimworld >
436 template< class DataHandle >
440 preAdapt();
441
446
448 typename Callback::DofVectorPointer callbackVector;
449 callbackVector.create( dofNumbering_.emptyDofSpace(), "Adaptation Callback" );
452 if( Callback::DofVectorPointer::supportsAdaptationData )
453 callbackVector.setAdaptationData( &dataHandler );
454 else
455 Alberta::adaptationDataHandler_ = &dataHandler;
456
457 bool refined = adapt();
458
459 if( !Callback::DofVectorPointer::supportsAdaptationData )
460 Alberta::adaptationDataHandler_ = 0;
461 callbackVector.release();
462
463 postAdapt();
464 return refined;
465 }
466
467
468 template< int dim, int dimworld >
469 inline const Alberta::GlobalVector &
471 ::getCoord ( const ElementInfo &elementInfo, int vertex ) const
472 {
473 assert( (vertex >= 0) && (vertex <= dim) );
474#if DUNE_ALBERTA_CACHE_COORDINATES
475 return coordCache_( elementInfo, vertex );
476#else
477 return elementInfo.coordinate( vertex );
478#endif
479 }
480
481
482 template < int dim, int dimworld >
484 {
485 return maxlevel_;
486 }
487
488
489 template< int dim, int dimworld >
490 inline int AlbertaGrid< dim, dimworld >::size ( int level, int codim ) const
491 {
492 return ((level >= 0) && (level <= maxlevel_) ? sizeCache_.size( level, codim ) : 0);
493 }
494
495
496 template< int dim, int dimworld >
497 inline int AlbertaGrid< dim, dimworld >::size ( int level, GeometryType type ) const
498 {
499 return ((level >= 0) && (level <= maxlevel_) ? sizeCache_.size( level, type ) : 0);
500 }
501
502
503 template< int dim, int dimworld >
504 inline int AlbertaGrid< dim, dimworld >::size ( int codim ) const
505 {
506 assert( sizeCache_.size( codim ) == mesh_.size( codim ) );
507 return mesh_.size( codim );
508 }
509
510
511 template< int dim, int dimworld >
512 inline int AlbertaGrid< dim, dimworld >::size ( GeometryType type ) const
513 {
514 return sizeCache_.size( type );
515 }
516
517
518 template < int dim, int dimworld >
519 inline const typename AlbertaGrid < dim, dimworld > :: Traits :: LevelIndexSet &
520 AlbertaGrid < dim, dimworld > :: levelIndexSet (int level) const
521 {
522 // assert that given level is in range
523 assert( (level >= 0) && (level < (int)levelIndexVec_.size()) );
524
525 if( levelIndexVec_[ level ] == 0 )
526 {
527 levelIndexVec_[ level ] = new typename GridFamily::LevelIndexSetImp ( dofNumbering_ );
528 levelIndexVec_[ level ]->update( lbegin< 0 >( level ), lend< 0 >( level ) );
529 }
530 return *(levelIndexVec_[ level ]);
531 }
532
533 template < int dim, int dimworld >
534 inline const typename AlbertaGrid < dim, dimworld > :: Traits :: LeafIndexSet &
535 AlbertaGrid < dim, dimworld > :: leafIndexSet () const
536 {
537 if( leafIndexSet_ == 0 )
538 {
539 leafIndexSet_ = new typename GridFamily::LeafIndexSetImp( dofNumbering_ );
540 leafIndexSet_->update( leafbegin< 0 >(), leafend< 0 >() );
541 }
542 return *leafIndexSet_;
543 }
544
545
546 template < int dim, int dimworld >
547 inline void AlbertaGrid < dim, dimworld >::calcExtras ()
549 // determine new maxlevel
550 maxlevel_ = levelProvider_.maxLevel();
551 assert( (maxlevel_ >= 0) && (maxlevel_ < MAXL) );
552
553 // unset up2Dat status, if lbegin is called then this status is updated
554 for( int l = 0; l < MAXL; ++l )
555 levelMarkerVector_[ l ].clear();
556
557 // unset up2Dat status, if leafbegin is called then this status is updated
558 leafMarkerVector_.clear();
559
560 sizeCache_.reset();
561
562 // update index sets (if they exist)
563 if( leafIndexSet_ != 0 )
564 leafIndexSet_->update( leafbegin< 0 >(), leafend< 0 >() );
565 for( unsigned int level = 0; level < levelIndexVec_.size(); ++level )
566 {
567 if( levelIndexVec_[ level ] )
568 levelIndexVec_[ level ]->update( lbegin< 0 >( level ), lend< 0 >( level ) );
569 }
570 }
571
572
573 template< int dim, int dimworld >
575 ::writeGrid ( const std::string &filename, ctype time ) const
576 {
577 if( filename.size() <= 0 )
578 DUNE_THROW( AlbertaIOError, "No filename given to writeGridXdr." );
579 return (mesh_.write( filename, time ) && hIndexSet_.write( filename ));
580 }
581
582
583 template< int dim, int dimworld >
585 ::readGrid ( const std::string &filename, ctype &time )
586 {
587 //removeMesh();
588
589 if( filename.size() <= 0 )
590 return false;
591
592 numBoundarySegments_ = mesh_.read( filename, time );
593 if( !mesh_ )
594 DUNE_THROW( AlbertaIOError, "Could not read grid file: " << filename << "." );
595
596 setup();
597 hIndexSet_.read( filename );
598
599 // calc maxlevel and indexOnLevel and so on
600 calcExtras();
601
602 return true;
603 }
604
605
606 // AlbertaGrid::AdaptationCallback
607 // -------------------------------
608
609 template< int dim, int dimworld >
610 template< class DataHandler >
611 struct AlbertaGrid< dim, dimworld >::AdaptationCallback
612 {
613 static const int dimension = dim;
614
616 typedef Alberta::Patch< dimension > Patch;
617
618 static DataHandler &getDataHandler ( const DofVectorPointer &dofVector )
619 {
620 DataHandler *dataHandler;
621 if( DofVectorPointer::supportsAdaptationData )
622 dataHandler = dofVector.getAdaptationData< DataHandler >();
623 else
624 dataHandler = (DataHandler *)Alberta::adaptationDataHandler_;
625 assert( dataHandler != 0 );
626 return *dataHandler;
627 }
628
629 static void interpolateVector ( const DofVectorPointer &dofVector,
630 const Patch &patch )
631 {
632 DataHandler &dataHandler = getDataHandler( dofVector );
633 for( int i = 0; i < patch.count(); ++i )
634 dataHandler.prolongLocal( patch, i );
635 }
636
637 static void restrictVector ( const DofVectorPointer &dofVector,
638 const Patch &patch )
639 {
640 DataHandler &dataHandler = getDataHandler( dofVector );
641 for( int i = 0; i < patch.count(); ++i )
642 dataHandler.restrictLocal( patch, i );
643 }
644 };
645
646} // namespace Dune
647
648#endif
Include standard header files.
Definition agrid.hh:60
static void checkAlbertaDimensions()
Definition albertagrid.cc:29
static const int dimWorld
Definition misc.hh:46
static void * adaptationDataHandler_
Definition albertagrid.cc:24
ALBERTA REAL_D GlobalVector
Definition misc.hh:50
[ provides Dune::Grid ]
Definition agrid.hh:109
static std::string typeName()
Definition agrid.hh:410
GridFamily::ctype ctype
Definition agrid.hh:143
Definition albertagrid/datahandle.hh:27
unsigned int create(const MacroData< dim > &macroData)
Definition meshpointer.hh:299
Definition dofvector.hh:179
const GlobalVector & coordinate(int vertex) const
Definition elementinfo.hh:685
void create()
Definition indexsets.cc:133
Definition albertagrid/indexsets.hh:329
Definition albertagrid/gridfamily.hh:98
Definition albertagrid/gridfamily.hh:117
Definition macrodata.hh:30
Definition misc.hh:32
Definition misc.hh:36
Definition albertagrid/projection.hh:80
Definition albertagrid/projection.hh:163
Definition refinement.hh:40
marker assigning subentities to one element containing them
Definition treeiterator.hh:35
A Traits struct that collects all associated types of one implementation.
Definition common/grid.hh:411