SDSL: Succinct Data Structure Library
A C++ template library for succinct data structures
 All Classes Namespaces Files Functions Variables Typedefs Friends
sdsl/include/sdsl/gap_vector.hpp
Go to the documentation of this file.
00001 /* sdsl - succinct data structures library
00002     Copyright (C) 2012 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 */
00022 #ifndef INCLUDED_SDSL_GAP_VECTOR
00023 #define INCLUDED_SDSL_GAP_VECTOR
00024 
00025 #include "int_vector.hpp"
00026 #include "util.hpp"
00027 
00029 namespace sdsl
00030 {
00031 
00032 template<bool b=true>// forward declaration needed for friend declaration
00033 class gap_rank_support;  // in gap_vector
00034 
00035 template<bool b=true>// forward declaration needed for friend declaration
00036 class gap_select_support;  // in gap_vector
00037 
00039 template<bool b=true>
00040 class gap_vector
00041 {
00042     public:
00043         typedef bit_vector::size_type size_type;
00044         typedef size_type value_type;
00045 
00046         friend class gap_rank_support<true>;
00047         friend class gap_select_support<true>;
00048 
00049         typedef gap_rank_support<true> rank_1_type;
00050         typedef gap_select_support<true> select_1_type;
00051     private:
00052         size_type m_size;
00053         int_vector<> m_position;
00054 
00055     public:
00056         gap_vector():m_size(0) {}
00057 
00058         gap_vector(const bit_vector& bv) {
00059             m_size = bv.size();
00060             if (m_size == 0)
00061                 return;
00062             size_type ones = util::get_one_bits(bv);
00063             m_position = int_vector<>(ones, 0, bit_magic::l1BP(m_size)+1);
00064             const uint64_t* bvp = bv.data();
00065             for (size_type i=0, one_cnt=0; i < (bv.size()+63)/64; ++i, ++bvp) {
00066                 if (*bvp) { // if there is a one in the word
00067                     for (size_type j=0; j<64 and 64*i+j < bv.size(); ++j) // check each bit of the word
00068                         if (bv[64*i+j]) {
00069                             m_position[one_cnt++] = 64*i+j;
00070                         }
00071                 }
00072             }
00073         }
00074 
00076         void swap(gap_vector& v) {
00077             if (this != &v) {
00078                 std::swap(m_size, v.m_size);
00079                 m_position.swap(v.m_position);
00080             }
00081         }
00082 
00084 
00089         value_type operator[](size_type i)const {
00090             // binary search the entries in m_position
00091             size_type lb=0, rb=m_position.size(), mid, pos;  // start interval [lb,rb)
00092             while (rb > lb) {
00093                 mid = (lb+rb)/2; // then mid>=lb mid<rb
00094                 pos = m_position[mid];
00095                 if (i > pos) {
00096                     lb = mid+1;
00097                 } else if (i < pos) {
00098                     rb = mid;
00099                 } else { // i == pos
00100                     return 1;
00101                 }
00102             }
00103             return 0;
00104         }
00105 
00107         size_type size()const {
00108             return m_size;
00109         }
00110 
00112         size_type serialize(std::ostream& out, structure_tree_node* v=NULL, std::string name="")const {
00113             size_type written_bytes = 0;
00114             structure_tree_node* child = structure_tree::add_child(v, name, util::class_name(*this));
00115             written_bytes += util::write_member(m_size, out, child, "size");
00116             written_bytes += m_position.serialize(out, child, "positions");
00117             structure_tree::add_size(child, written_bytes);
00118             return written_bytes;
00119         }
00120 
00122         void load(std::istream& in) {
00123             util::read_member(m_size, in);
00124             m_position.load(in);
00125         }
00126 };
00127 
00128 template<bool b>
00129 class gap_rank_support
00130 {
00131     public:
00132         typedef bit_vector::size_type size_type;
00133         typedef gap_vector<b> bit_vector_type;
00134     private:
00135         const bit_vector_type* m_v;
00136 
00137     public:
00138 
00139         gap_rank_support(const bit_vector_type* v=NULL) {
00140             init(v);
00141         }
00142 
00143         void init(const bit_vector_type* v=NULL) {
00144             set_vector(v);
00145         }
00146 
00147         size_type rank(size_type i)const {
00148             // binary search the entries in m_position
00149             size_type lb=0, rb=m_v->m_position.size(), mid, pos=0;  // start interval [lb,rb)
00150             while (rb > lb) {
00151                 mid = (lb+rb)/2; // then mid>=lb mid<rb
00152                 pos = m_v->m_position[mid];
00153                 if (i <= pos) {
00154                     rb = mid;
00155                 } else {
00156                     lb = mid+1;
00157                 }
00158             } // m_position[rb] >= i
00159             return rb;
00160         }
00161 
00162         const size_type operator()(size_type i)const {
00163             return rank(i);
00164         }
00165 
00166         const size_type size()const {
00167             return m_v->size();
00168         }
00169 
00170         void set_vector(const bit_vector_type* v=NULL) {
00171             m_v = v;
00172         }
00173 
00174         gap_rank_support& operator=(const gap_rank_support& rs) {
00175             if (this != &rs) {
00176                 set_vector(rs.m_v);
00177             }
00178             return *this;
00179         }
00180 
00181         void swap(gap_rank_support& rs) { }
00182 
00183         bool operator==(const gap_rank_support& ss)const {
00184             if (this == &ss)
00185                 return true;
00186             return ss.m_v == m_v;
00187         }
00188 
00189         bool operator!=(const gap_rank_support& rs)const {
00190             return !(*this == rs);
00191         }
00192 
00193 
00194         void load(std::istream& in, const bit_vector_type* v=NULL) {
00195             set_vector(v);
00196         }
00197 
00198         size_type serialize(std::ostream& out, structure_tree_node* v=NULL, std::string name="")const {
00199             structure_tree_node* child = structure_tree::add_child(v, name, util::class_name(*this));
00200             size_type written_bytes = 0;
00201             structure_tree::add_size(child, written_bytes);
00202             return written_bytes;
00203         }
00204 };
00205 
00206 
00207 
00208 
00209 template<bool b>
00210 class gap_select_support
00211 {
00212     public:
00213         typedef bit_vector::size_type size_type;
00214         typedef gap_vector<b> bit_vector_type;
00215     private:
00216         const bit_vector_type* m_v;
00217 
00218     public:
00219 
00220         gap_select_support(const bit_vector_type* v=NULL) {
00221             init(v);
00222         }
00223 
00224         void init(const bit_vector_type* v=NULL) {
00225             set_vector(v);
00226         }
00227 
00229         size_type select(size_type i)const {
00230             return m_v->m_position[i-1];
00231         }
00232 
00233         const size_type operator()(size_type i)const {
00234             return select(i);
00235         }
00236 
00237         const size_type size()const {
00238             return m_v->size();
00239         }
00240 
00241         void set_vector(const bit_vector_type* v=NULL) {
00242             m_v = v;
00243         }
00244 
00245         gap_select_support& operator=(const gap_select_support& rs) {
00246             if (this != &rs) {
00247                 set_vector(rs.m_v);
00248             }
00249             return *this;
00250         }
00251 
00252         void swap(gap_select_support& rs) { }
00253 
00254         bool operator==(const gap_select_support& ss)const {
00255             if (this == &ss)
00256                 return true;
00257             return ss.m_v == m_v;
00258         }
00259 
00260         bool operator!=(const gap_select_support& rs)const {
00261             return !(*this == rs);
00262         }
00263 
00264 
00265         void load(std::istream& in, const bit_vector_type* v=NULL) {
00266             set_vector(v);
00267         }
00268 
00269         size_type serialize(std::ostream& out, structure_tree_node* v=NULL, std::string name="")const {
00270             structure_tree_node* child = structure_tree::add_child(v, name, util::class_name(*this));
00271             size_type written_bytes = 0;
00272             structure_tree::add_size(child, written_bytes);
00273             return written_bytes;
00274         }
00275 };
00276 
00277 }
00278 
00279 #endif