topologyfactory.hh

Go to the documentation of this file.
00001 #ifndef DUNE_TOPOLOGYFACTORY_HH
00002 #define DUNE_TOPOLOGYFACTORY_HH
00003 
00004 #include <vector>
00005 #include <map>
00006 
00007 #include <dune/common/fvector.hh>
00008 #include <dune/grid/genericgeometry/conversion.hh>
00009 #include <dune/grid/genericgeometry/topologytypes.hh>
00010 
00011 namespace Dune 
00012 {
00013 
00032   template <class Traits>
00033   struct TopologyFactory
00034   {
00035     // extract types from Traits class
00036     static const unsigned int dimension = Traits::dimension;
00037     typedef typename Traits::Key Key;
00038     typedef typename Traits::Object Object;
00039     typedef typename Traits::Factory Factory;
00041     static Object *create(unsigned int topologyId, const Key &key) DUNE_DEPRECATED
00042     {
00043       Object *object;
00044       GenericGeometry::IfTopology< Maker, dimension >::apply( topologyId, key, object );
00045       return object;
00046     }
00048     static Object *create(const Dune::GeometryType &gt, const Key &key) 
00049     {
00050       Object *object;
00051       GenericGeometry::IfTopology< Maker, dimension >::apply( gt.id(), key, object );
00052       return object;
00053     }
00055     template <class Topology>
00056     static Object *create(const Key &key) 
00057     {
00058       return Factory::template createObject<Topology> ( key );
00059     }
00061     static void release( Object *object) 
00062     {
00063       delete object;
00064     }
00065     private:
00066     // Internal maker class used in ifTopology helper
00067     template< class Topology >
00068     struct Maker
00069     {
00070       static void apply ( const Key &key, Object *&object )
00071       {
00072         object = create<Topology>( key );
00073       };
00074     };
00075   };
00076 
00077 
00082   template <class Factory>
00083   struct TopologySingletonFactory
00084   {
00085     static const unsigned int dimension = Factory::dimension;
00086     typedef typename Factory::Key Key;
00087     typedef const typename Factory::Object Object;
00089     static Object *create ( const unsigned int topologyId, const Key &key ) DUNE_DEPRECATED
00090     {
00091       assert( topologyId < numTopologies );
00092       return create( Dune::GeometryType( topologyId, dimension ), key );
00093     }
00095     static Object *create ( const Dune::GeometryType &gt, const Key &key )
00096     {
00097       assert( gt.id() < numTopologies );
00098       return instance().getObject( gt, key );
00099     }
00101     template< class Topology >
00102     static Object *create ( const Key &key )
00103     {
00104       dune_static_assert( (Topology::dimension == dimension),
00105                      "Topology with incompatible dimension used" );
00106       return instance().template getObject< Topology >( key );
00107     }
00109     static void release ( Object *object )
00110     {}
00111   private:
00112     static TopologySingletonFactory &instance ()
00113     {
00114       static TopologySingletonFactory instance;
00115       return instance;
00116     }
00117 
00118     static const unsigned int numTopologies = (1 << dimension);
00119     typedef FieldVector< Object *, numTopologies > Array;
00120     typedef std::map< Key, Array > Storage;
00121 
00122     TopologySingletonFactory ()
00123     {}
00124     ~TopologySingletonFactory ()
00125     {
00126       const typename Storage::iterator end = storage_.end();
00127       for( typename Storage::iterator it = storage_.begin(); it != end; ++it )
00128       {
00129         for( unsigned int topologyId = 0; topologyId < numTopologies; ++topologyId )
00130         {
00131           Object *&object = it->second[ topologyId ];
00132           if( object != 0 )
00133             Factory::release( object );
00134           object = 0;
00135         }
00136       }
00137     }
00138 
00139     Object *&find( const unsigned int topologyId, const Key &key )
00140     {
00141       typename Storage::iterator it = storage_.find( key );
00142       if( it == storage_.end() )
00143         it = storage_.insert( std::make_pair( key, Array( 0 ) ) ).first;
00144       return it->second[ topologyId ];
00145     }
00146 
00147     Object *getObject ( const Dune::GeometryType &gt, const Key &key )
00148     {
00149       Object *&object = find( gt.id(), key );
00150       if( object == 0 )
00151         object = Factory::create( gt, key );
00152       return object;
00153     }
00154 
00155     template< class Topology >
00156     Object *getObject ( const Key &key )
00157     {
00158       Object *&object = find(Topology::id,key);
00159       if( object == 0 )
00160         object = Factory::template create< Topology >( key );
00161       return object;
00162     }
00163     Storage storage_;
00164   };
00165 
00166 }
00167 
00168 #endif // #ifndef DUNE_TOPOLOGYFACTORY_HH

Generated on Fri Apr 29 2011 with Doxygen (ver 1.7.1) [doxygen-log,error-log].