vdj_pipe
pipeline for processing DNA sequence data
id_map.hpp
Go to the documentation of this file.
1 
7 #ifndef ID_MAP_HPP_
8 #define ID_MAP_HPP_
9 #include <vector>
10 #include "boost/assert.hpp"
13 #include "vdj_pipe/exception.hpp"
14 
15 namespace vdj_pipe{ namespace detail{
16 
19 template<class Id, class Obj, template<class,class> class Stor = std::vector >
20 class Id_map{
21  typedef Stor<Obj, std::allocator<Obj> > vector_t;
22 
23 public:
24  typedef Id_map self_type;
25  typedef Id id_type;
26  typedef Obj value_type;
27  typedef typename vector_t::iterator iterator;
28  typedef typename vector_t::const_iterator const_iterator;
29  typedef base_exception Err;
30 
31  explicit Id_map(const id_type id0)
32  : vid_(),
33  erased_(),
34  id0_(id0)
35  {}
36 
37  std::size_t size() const { return vid_.size() - erased_.size(); }
38  const_iterator begin() const {return vid_.begin();}
39  const_iterator end() const {return vid_.end();}
40  bool empty() const {return !(vid_.size() - erased_.size());}
41  id_type min_id() const {return id0_;}
42  id_type max_id() const {return pos2id(vid_.size()-1);}
43  void reserve(const id_type id) {vid_.reserve(vpos(id) + 1);}
44 
45  value_type const& operator[](const id_type id) const {
46  BOOST_ASSERT( check_range(id) && "invalid ID" );
47  return vid_[vpos(id)];
48  }
49 
50  value_type& operator[](const id_type id) {
51  BOOST_ASSERT( check_range(id) && "invalid ID" );
52  return vid_[vpos(id)];
53  }
54 
55  value_type const& at(const id_type id) const {
56  if( ! check_range(id) ) BOOST_THROW_EXCEPTION(
57  Err()
58  << Err::msg_t("invalid ID")
59  << Err::int1_t(id())
60  );
61  return vid_[vpos(id)];
62  }
63 
64  value_type& at(const id_type id) {
65  if( ! check_range(id) ) BOOST_THROW_EXCEPTION(
66  Err()
67  << Err::msg_t("invalid ID")
68  << Err::int1_t(id())
69  );
70  return vid_[vpos(id)];
71  }
72 
73  value_type const* find(const id_type id) const {
74  if( check_range(id) ) return & this->operator[](id);
75  return 0;
76  }
77 
78  value_type* find(const id_type id) {
79  if( check_range(id) ) return & this->operator[](id);
80  return 0;
81  }
82 
83  id_type insert(value_type const& obj) {
84  if( erased_.empty() ) {
85  const id_type id = pos2id(vid_.size());
86  vid_.push_back(obj);
87  return id;
88  }
89  const id_type id = erased_.back();
90  erased_.pop_back();
91  const std::size_t n = vpos(id);
92  BOOST_ASSERT(vid_.size() > n);
93  vid_[n] = obj;
94  return id;
95  }
96 
101  value_type& insert(const id_type id) {
102  const std::size_t n = vpos(id);
103  if( (! erased_.erase(id)) && (n >= vid_.size()) ) {
104  vid_.resize(n + 1);
105  }
106  return vid_[n];
107  }
108 
109  void erase(const id_type id) {
110  BOOST_ASSERT( check_range(id) );
111  const std::size_t pos = vpos(id);
112  erased_.insert(id);
113  vid_[pos] = value_type();
114  }
115 
116  void clear() {
117  erased_.clear();
118  vid_.clear();
119  }
120 
121 private:
122  vector_t vid_;
123  Vector_set<id_type> erased_;
124  id_type id0_;
125 
126  std::size_t vpos(const id_type id) const {
127  BOOST_ASSERT(id >= id0_ && "invalid ID");
128  return id() - id0_();
129  }
130 
131  id_type pos2id(const std::size_t n) const {return id_type(n + id0_());}
132 
133  bool check_range(const id_type id) const {
134  return id >= id0_ && vpos(id) < vid_.size();
135  }
136 };
137 
138 }//namespace detail
139 }//namespace vdj_pipe
140 #endif /* ID_MAP_HPP_ */
Main namespace of vdj_pipe library.
Definition: sequence_file.hpp:14
Definition: id_map.hpp:20
value_type & insert(const id_type id)
Definition: id_map.hpp:101
Definition: exception.hpp:23