Main Page | Namespace List | Class Hierarchy | Class List | Directories | File List | Namespace Members | Class Members | File Members

inhomogeneous_trie/trie_manipulators/sequence/IntersectProPruner.hpp

Go to the documentation of this file.
00001 #ifndef IntersectProPruner_HPP
00002 #define IntersectProPruner_HPP
00003 
00004 #include "common.hpp"
00005 #include "common/Edge.hpp"
00006 #include "apriori/bodon/inhomogeneous_trie/trie_manipulators/ManipulatorBase.hpp"
00007 #include <vector>
00008 //#include <cstdio>
00009 //#include <iterator>   //for test
00010 
00011 
00012 
00013 
00014 namespace Bodon
00015 {
00016 namespace sequence
00017 {
00018 namespace inhomogeneous_trie
00019 {
00020    template <class DF_D, class TRIE, class LEAF, class LEAF_ALLOCATOR>
00021    class IntersectProPruner : public 
00022    Bodon::inhomogeneous_trie::ManipulatorBase<DF_D, TRIE, LEAF_ALLOCATOR>
00023    {
00024       private:
00025          typedef Bodon::inhomogeneous_trie::ManipulatorBase<DF_D, TRIE, LEAF_ALLOCATOR> PARENT;
00026       protected:
00027          std::vector<Edge> extenders;
00028          mutable std::vector<item_t> ext_items;
00029          mutable std::vector<item_t> ext_nee;
00030          std::vector<Edge> replace_list;
00031 
00032       public:
00033          IntersectProPruner( TRIE& main_trie, DF_D& df_decoder,
00034                              LEAF_ALLOCATOR& s_alloc ) :
00035             Bodon::inhomogeneous_trie::ManipulatorBase<DF_D, TRIE, LEAF_ALLOCATOR>(
00036                main_trie, df_decoder, s_alloc){}
00037 
00038       protected:
00039          
00040          void intersect( const TRIE* subset_trie ) const;
00041 
00042          void filterNonExtenders( 
00043             const std::vector<const TRIE*>& subset_tries,
00044             const item_t leaf_item ) const;
00045 
00046          bool findSubsetTries( 
00047             std::vector<item_t>& itemset, 
00048             std::vector<const TRIE*>& subset_trie) const;
00049 
00050          void generateCandidateAtParent(
00051             TRIE* trie, std::vector<item_t>& maybe_candidate);
00052 
00053 
00054    };
00055 
00056    template <class DF_D, class TRIE, class LEAF, class LEAF_ALLOCATOR> inline void 
00057    IntersectProPruner<DF_D, TRIE, LEAF, LEAF_ALLOCATOR>::
00058    intersect( const TRIE* subset_trie) const
00059    {
00060       typename TRIE::const_iterator it_e( subset_trie->edgelist.begin() );
00061       std::vector<item_t>::iterator it_i(ext_items.begin());
00062       while(it_e != subset_trie->edgelist.end() && it_i != ext_items.end())
00063       {
00064          if(*it_e < *it_i)
00065             ++it_e;
00066          else if(*it_e > *it_i)
00067             it_i = ext_items.erase(it_i);
00068          else
00069          {
00070             ++it_e;
00071             ++it_i;
00072          }
00073       }
00074       ext_items.erase(it_i, ext_items.end());      
00075    }
00076 
00077 
00078    template <class DF_D, class TRIE, class LEAF, class LEAF_ALLOCATOR> inline void 
00079    IntersectProPruner<DF_D, TRIE, LEAF, LEAF_ALLOCATOR>::
00080    filterNonExtenders( const std::vector<const TRIE*>& subset_tries,  
00081                        const item_t leaf_item ) const
00082    {
00083       std::vector<typename TRIE::const_iterator> subset_child_iters;
00084       subset_child_iters.reserve(subset_tries.size());
00085       for(typename std::vector<const TRIE*>::const_iterator it = subset_tries.begin(); 
00086           it !=  subset_tries.end(); ++it)
00087          subset_child_iters.push_back((*it)->edgelist.begin());
00088 
00089       for(std::vector<item_t>::size_type index = 0; 
00090           index < subset_tries.size(); ++index)
00091       {
00092          while( subset_child_iters[index] !=  subset_tries[index]->edgelist.end() &&
00093                 (*(subset_child_iters[index])).first < leaf_item)
00094             ++subset_child_iters[index];
00095          if( subset_child_iters[index] !=  subset_tries[index]->edgelist.end() &&
00096              (*(subset_child_iters[index])).first == leaf_item)
00097             intersect(static_cast<const TRIE*>((*(subset_child_iters[index])).second));
00098          else
00099          {
00100             ext_items.clear();
00101             break;
00102          }
00103       }
00104    }
00105 
00106 
00107    template <class DF_D, class TRIE, class LEAF, class LEAF_ALLOCATOR> inline bool
00108    IntersectProPruner<DF_D, TRIE, LEAF, LEAF_ALLOCATOR>::
00109    findSubsetTries( std::vector<item_t>& itemset, 
00110                     std::vector<const TRIE*>& subset_tries ) const
00111    {
00112       assert(itemset.size() > 0);
00113       std::vector<item_t>::iterator item_it = itemset.end()-1;
00114       register item_t deleted_item = *item_it, temp_item;
00115       const TRIE* a_subset_trie;
00116 
00117       itemset.pop_back();
00118       a_subset_trie = PARENT::main_trie.isIncluded( itemset, itemset.begin() );
00119       if(a_subset_trie)
00120          subset_tries.push_back(a_subset_trie);
00121       else 
00122       {
00123          itemset.push_back(deleted_item);
00124          return false;
00125       }
00126       while(item_it != itemset.begin() )
00127       {
00128          --item_it;
00129          temp_item = *item_it;
00130          *item_it = deleted_item;
00131          deleted_item = temp_item;
00132          a_subset_trie = PARENT::main_trie.isIncluded( itemset, itemset.begin() );
00133          if(a_subset_trie)
00134             subset_tries.push_back(a_subset_trie);
00135          else
00136          {
00137             itemset.insert( item_it, deleted_item );
00138             return false;
00139          }
00140       }
00141       itemset.insert( item_it, deleted_item );
00142       return true;
00143    }
00144 
00145    template <class DF_D, class TRIE, class LEAF, class LEAF_ALLOCATOR> 
00146    inline void IntersectProPruner<DF_D, TRIE, LEAF, LEAF_ALLOCATOR>::
00147    generateCandidateAtParent(TRIE* trie, std::vector<item_t>& maybe_candidate)
00148    {
00149       std::vector<const TRIE*> subset_tries;
00150       const bool all_subset_included = findSubsetTries( 
00151          maybe_candidate, subset_tries);
00152       typename TRIE::iterator itEdge2;
00153       LEAF* toExtendAsLeaf;
00154       TRIE* toExtend;
00155       replace_list.clear();
00156       for( typename TRIE::iterator itEdge( trie->edgelist.begin() ); 
00157              itEdge != trie->edgelist.end(); ++itEdge )
00158       {
00159          toExtendAsLeaf = static_cast<LEAF*>((*itEdge).second);
00160          PARENT::df_decoder.pushItemWithWrite( (*itEdge).first, 
00161                                        toExtendAsLeaf->getCounter() );
00162          PARENT::df_decoder.popItem();
00163          if(all_subset_included)
00164          {
00165             ext_items.clear();
00166             for( itEdge2 = trie->edgelist.begin(); 
00167                  itEdge2 != trie->edgelist.end(); ++itEdge2 )
00168                ext_items.push_back((*itEdge2).first);
00169             filterNonExtenders( subset_tries, (*itEdge).first );
00170             if(ext_items.empty())
00171             {
00172                toExtendAsLeaf->setCounter(0);
00173                replace_list.push_back(Edge((*itEdge).first, toExtendAsLeaf));
00174             }
00175             else
00176             {
00177                extenders.clear();
00178                for(std::vector<item_t>::iterator it = ext_items.begin();
00179                    it != ext_items.end(); ++it)
00180                {
00181                   extenders.push_back(Edge(*it, PARENT::s_alloc.allocate()));
00182                   static_cast<LEAF*>(extenders.back().second)->setCounter(0);
00183                }
00184                toExtend = new TRIE(toExtendAsLeaf->getCounter());
00185                PARENT::s_alloc.free(toExtendAsLeaf);
00186                replace_list.push_back(Edge((*itEdge).first, toExtend));
00187                toExtend->edgelist.insert(extenders);
00188             }
00189          }
00190          else
00191          {
00192             toExtendAsLeaf->setCounter(0);
00193             replace_list.push_back(Edge((*itEdge).first, toExtendAsLeaf));
00194          }
00195       }
00196       trie->edgelist.clear();
00197       trie->edgelist.insert(replace_list);
00198    }
00199 }
00200 }
00201 }
00202 #endif

Generated on Sun Sep 17 17:50:39 2006 for FIM environment by  doxygen 1.4.4