SDSL: Succinct Data Structure Library
A C++ template library for succinct data structures
 All Classes Namespaces Files Functions Variables Typedefs Friends
sdsl/include/sdsl/rmq_succinct_sada.hpp
Go to the documentation of this file.
00001 /* sdsl - succinct data structures library
00002     Copyright (C) 2009 Simon Gog
00003 
00004     This program is free software: you can redistribute it and/or modify
00005     it under the terms of the GNU General Public License as published by
00006     the Free Software Foundation, either version 3 of the License, or
00007     (at your option) any later version.
00008 
00009     This program is distributed in the hope that it will be useful,
00010     but WITHOUT ANY WARRANTY; without even the implied warranty of
00011     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00012     GNU General Public License for more details.
00013 
00014     You should have received a copy of the GNU General Public License
00015     along with this program.  If not, see http://www.gnu.org/licenses/ .
00016 */
00021 #ifndef INCLUDED_SDSL_RMQ_SUCCINCT_SADA
00022 #define INCLUDED_SDSL_RMQ_SUCCINCT_SADA
00023 
00024 #include "rmq_support.hpp"
00025 #include "int_vector.hpp"
00026 #include "algorithms_for_compressed_suffix_trees.hpp"
00027 #include "bp_support_sada.hpp"
00028 #include "rank_support_v.hpp"
00029 #include "select_support_mcl.hpp"
00030 #include "util.hpp"
00031 
00033 namespace sdsl
00034 {
00035 
00036 
00037 template<bool Minimum = true, class Bp_support = bp_support_sada<256, 32, rank_support_v5<>, select_support_dummy>, 
00038              class Rank_support10 = rank_support_v<10,2>, class Select_support10 = select_support_mcl<10,2> >
00039 class rmq_succinct_sada;
00040 
00041 template<class Bp_support = bp_support_sada<256, 32, rank_support_v5<>, select_support_dummy>, 
00042              class Rank_support10 = rank_support_v<10,2>, class Select_support10 = select_support_mcl<10,2> >
00043 struct range_maximum_support_sada {
00044     typedef rmq_succinct_sada<false, Bp_support, Rank_support10, Select_support10> type;
00045 };
00046 
00048 
00061 template<bool Minimum, class Bp_support, class Rank_support10, class Select_support10>
00062 class rmq_succinct_sada
00063 {
00064         bit_vector                                      m_ect_bp;                       
00065         Bp_support                                      m_ect_bp_support;       
00066         Rank_support10                          m_ect_bp_rank10;                
00067         Select_support10                        m_ect_bp_select10;      
00068 
00069     public:
00070         typedef typename bit_vector::size_type size_type;
00071         typedef typename bit_vector::size_type value_type;
00072 
00073         typedef Bp_support                      bp_support_type;
00074         typedef Rank_support10          rank_support10_type;
00075         typedef Select_support10        select_support10_type;
00076 
00077         const bit_vector&                ect_bp;
00078         const Bp_support&                ect_bp_support;
00079         const Rank_support10&   ect_bp_rank10;
00080         const Select_support10& ect_bp_select10;
00081 
00082     private:
00083 
00084         typedef rmq_succinct_sct<Minimum> rmq_construct_helper_type;
00085 
00086         void _construct_bp_of_extended_cartesian_tree(size_type l, size_type r, size_type& bp_cnt, const rmq_construct_helper_type& rmq_helper) {
00087             if (r==(size_type)-1 or l > r)
00088                 return;
00089             m_ect_bp[bp_cnt++] = 1; // write beginning of inner node
00090             size_type m = rmq_helper(l, r);
00091             _construct_bp_of_extended_cartesian_tree(l, m-1, bp_cnt, rmq_helper);
00092             m_ect_bp[bp_cnt++] = 1; // write leaf
00093             m_ect_bp[bp_cnt++] = 0;
00094             _construct_bp_of_extended_cartesian_tree(m+1, r, bp_cnt, rmq_helper);
00095             m_ect_bp[bp_cnt++] = 0; // write end of inner node
00096             assert(bp_cnt <= m_ect_bp.size());
00097         }
00098 
00099                 template<class RandomAccessContainer>
00100         void construct(const RandomAccessContainer* v) {
00101             if (v == NULL) {
00102                 m_ect_bp = bit_vector(0); m_ect_bp_support = Bp_support();
00103                 m_ect_bp_rank10 = Rank_support10(); m_ect_bp_select10 = Select_support10();
00104             } else {
00105                 rmq_construct_helper_type rmq_helper(v);
00106                 m_ect_bp.resize(4*v->size());
00107                 size_type bp_cnt=0;
00108                 _construct_bp_of_extended_cartesian_tree((size_type)0, v->size()-1, bp_cnt, rmq_helper);
00109                 assert(bp_cnt == 4*v->size());
00110                 m_ect_bp_support = Bp_support(&m_ect_bp);
00111                 util::init_support(m_ect_bp_rank10, &m_ect_bp);
00112                 util::init_support(m_ect_bp_select10, &m_ect_bp);
00113             }
00114         }
00115 
00116         void copy(const rmq_succinct_sada& rm) {
00117             m_ect_bp = rm.m_ect_bp;
00118             m_ect_bp_support = rm.m_ect_bp_support;
00119             m_ect_bp_support.set_vector(&m_ect_bp);
00120             m_ect_bp_rank10 = rm.m_ect_bp_rank10;
00121             m_ect_bp_rank10.set_vector(&m_ect_bp);
00122             m_ect_bp_select10 = rm.m_ect_bp_select10;
00123             m_ect_bp_select10.set_vector(&m_ect_bp);
00124         }
00125 
00126     public:
00128         rmq_succinct_sada():ect_bp(m_ect_bp), ect_bp_support(m_ect_bp_support), ect_bp_rank10(m_ect_bp_rank10), ect_bp_select10(m_ect_bp_select10) {}
00129 
00131                 template<class RandomAccessContainer>
00132         rmq_succinct_sada(const RandomAccessContainer* v=NULL):ect_bp(m_ect_bp), ect_bp_support(m_ect_bp_support), ect_bp_rank10(m_ect_bp_rank10), ect_bp_select10(m_ect_bp_select10) {
00133             construct(v);
00134         }
00135 
00137         rmq_succinct_sada(const rmq_succinct_sada& rm):ect_bp(m_ect_bp), ect_bp_support(m_ect_bp_support), ect_bp_rank10(m_ect_bp_rank10), ect_bp_select10(m_ect_bp_select10) {
00138             if (this != &rm) { // if v is not the same object
00139                 copy(rm);
00140             }
00141         }
00142 
00144         ~rmq_succinct_sada() { }
00145 
00146         rmq_succinct_sada& operator=(const rmq_succinct_sada& rm) {
00147             if (this != &rm) {
00148                 copy(rm);
00149             }
00150             return *this;
00151         }
00152 
00154         void swap(const rmq_succinct_sada& rm) {
00155             m_ect_bp.swap(rm.m_ect_bp);
00156                         util::swap_support(m_ect_bp_support, rm.m_ect_bp_support, 
00157                                                   &m_ect_bp, &(rm.m_ect_bp));
00158                         util::swap_support(m_ect_bp_rank10, rm.m_ect_bp_rank10, 
00159                                                   &m_ect_bp, &(rm.m_ect_bp));
00160                         util::swap_support(m_ect_bp_select10, rm.m_ect_bp_select10,
00161                                                   &m_ect_bp, &(rm.m_ect_bp));
00162         }
00163 
00165 
00175         size_type operator()(const size_type l, const size_type r)const {
00176             assert(l <= r); assert(r < size());
00177             if (l==r)
00178                 return l;
00179             size_type x         = m_ect_bp_select10(l+1);
00180             size_type y         = m_ect_bp_select10(r+1);
00181             size_type z         = m_ect_bp_support.rmq(x, y);
00182             size_type f         = z + 1 - 2*(m_ect_bp[z]);
00183             return m_ect_bp_rank10(f-1);
00184         }
00185 
00186         size_type size()const {
00187             return m_ect_bp.size()/4;
00188         }
00189 
00190         size_type serialize(std::ostream& out, structure_tree_node* v=NULL, std::string name="")const {
00191                 structure_tree_node* child = structure_tree::add_child(v, name, util::class_name(*this));
00192             size_type written_bytes = 0;
00193             written_bytes += m_ect_bp.serialize(out, child, "ect_bp");
00194             written_bytes += m_ect_bp_support.serialize(out, child, "ect_bp_support");
00195             written_bytes += m_ect_bp_rank10.serialize(out, child, "ect_bp_rank10");
00196             written_bytes += m_ect_bp_select10.serialize(out, child, "ect_bp_select10");
00197                 structure_tree::add_size(child, written_bytes);
00198             return written_bytes;
00199         }
00200 
00201         void load(std::istream& in) {
00202             m_ect_bp.load(in);
00203             m_ect_bp_support.load(in, &m_ect_bp);
00204             m_ect_bp_rank10.load(in, &m_ect_bp);
00205             m_ect_bp_select10.load(in, &m_ect_bp);
00206         }
00207 };
00208 
00209 
00210 }
00211 
00212 
00213 #endif