Jafar
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines
IdFactory.hpp
00001 /* $Id$ */
00002 
00003 #ifndef _IDMAKER_HPP_
00004 #define _IDMAKER_HPP_
00005 
00006 #include <list>
00007 #include <set>
00008 #include <iostream>
00009 
00010 namespace jafar {
00011   namespace kernel {
00012     
00030     template <typename T>
00031     class IdCollectorNone
00032     {
00033       public:
00034         bool empty() { return true; }         
00035         T get() { return 0; }                 
00036         bool collect(T id) { return false; }  
00037         T size() { return 0; }                
00038         void clear() {}                       
00039         T defrag(T lastid) { return lastid; } 
00040     };
00041     
00049     template <typename T>
00050     class IdCollectorList
00051     {
00052       private:
00053         typedef std::list<T> storage_t;
00054         storage_t freed;
00055       public:
00056         bool empty() { return freed.empty(); }
00057         T get() { T res = freed.front(); freed.pop_front(); return res; }
00058         bool collect(T id) { freed.push_back(id); return true; }
00059         T size() { return freed.size(); }
00060         void clear() { freed.clear(); }
00061         T defrag(T lastid) { return lastid; } // would be too expensive to do something (at least n*log(n))
00062     };
00063     
00070     template <typename T>
00071     class IdCollectorSet
00072     {
00073       private:
00074         typedef std::set<T> storage_t;
00075         storage_t freed;
00076       public:
00077         bool empty() { return freed.empty(); }
00078         T get() { T res = *freed.begin(); freed.erase(freed.begin()); return res; }
00079         bool collect(T id) { return freed.insert(id).second; }
00080         T size() { return freed.size(); }
00081         void clear() { freed.clear(); }
00082         T defrag(T lastid)
00083         {
00084           typename storage_t::reverse_iterator rit;
00085           for(rit = freed.rbegin(); !freed.empty() && *rit == lastid; --lastid)
00086           {
00087             freed.erase(--rit.base());
00088             if (!freed.empty()) ++rit;
00089           }
00090           return lastid; 
00091         }
00092     };
00093     
00100     template <typename T = unsigned, template<typename> class IdCollector = IdCollectorNone>
00101     class IdFactory {
00102       public:
00103         IdFactory() : m_lastId(0) {}
00104         ~IdFactory() {}
00105 
00106         typedef T storage_t;
00107         
00109         T getId()
00110         {
00111           T id = (freed.empty() ? ++m_lastId : freed.get());
00112 //std::cout << "IdFactory::getId " << id << std::endl;
00113           return id;
00114         }
00115         
00117         bool releaseId(T id) 
00118         {
00119 //std::cout << "IdFactory::releaseId " << id << std::endl;
00120           if (id == 0 || id > m_lastId) return false;
00121           if (id == m_lastId ) 
00122             m_lastId = freed.defrag(m_lastId-1); 
00123           else 
00124             return freed.collect(id);
00125           return true;
00126         }
00127         
00129         void reset() { m_lastId = 0; freed.clear(); }
00130         
00132         T countUsed() { return m_lastId-freed.size(); }
00133         
00135         T countCollected() { return freed.size(); }
00136       private:
00137         T m_lastId;
00138         IdCollector<T> freed;
00139     };
00140     
00141     typedef IdFactory<unsigned, IdCollectorNone> IdFactoryNone;
00142     typedef IdFactory<unsigned, IdCollectorList> IdFactoryList;
00143     typedef IdFactory<unsigned, IdCollectorSet> IdFactorySet;
00144   }
00145 }
00146 
00147 #endif
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines

Generated on Wed Oct 15 2014 00:37:24 for Jafar by doxygen 1.7.6.1
LAAS-CNRS