码迷,mamicode.com
首页 > 其他好文 > 详细

[转]An STL compliant sorted vector-源码示例

时间:2015-02-11 12:35:13      阅读:158      评论:0      收藏:0      [点我收藏+]

标签:

 

        原文地址:http://www.codeproject.com/Articles/3217/An-STL-compliant-sorted-vector

      最近在看sorted vectored的一些东西,自己封装了一个sorted vector类型,后来找到了codeproject上的一个源码示例,感觉写的不错,可以借鉴一下。

      sorted_vector adapts a std::vector to the interface required by std::set/std::multiset, thereby providing set/multiset and vector functionality (random access) in one container.

  1 /* STL-conforming "sorted vector" container
  2  *
  3  * (C) 2002 Martin Holzherr (holzherr@infobrain.com). All rights reserved.
  4  *
  5  * Permission is granted to use, distribute and modify this code provided that:
  6  *   · this copyright notice appears,
  7  *   · 
  8  * The author welcomes any suggestions on the code or reportings of actual
  9  * use of the code. Please send your comments to holzherr@infobrain.com.
 10  *
 11  * The author makes NO WARRANTY or representation, either express or implied,
 12  * with respect to this code, its quality, accuracy, merchantability, or
 13  * fitness for a particular purpose.  This software is provided "AS IS", and
 14  * you, its user, assume the entire risk as to its quality and accuracy.
 15  *
 16  * Created:            November 19th, 2002
 17  * Last modified:    November 27th, 2002 
 18                         (changed namespace from std to codeproject;
 19                         uses template member functions for MSCVER>=1300)
 20                                 
 21  */
 22 
 23 #ifndef SORTED_VECTOR_
 24 #define SORTED_VECTOR_
 25 #define VERSION_SORTED_VECTOR_ 0x00010010
 26 
 27 
 28 #include <algorithm>
 29 #include <vector>
 30 #include <utility>
 31 #include <functional>
 32 
 33 #pragma pack(push,8)
 34 #pragma warning(push,3)
 35 
 36 
 37 namespace codeproject{
 38         // TEMPLATE CLASS sorted_vector
 39 
 40     template<class K, bool bNoDuplicates= false,class Pr = std::less<K>, class A = std::allocator<K> >
 41     class sorted_vector {
 42 public:
 43     typedef sorted_vector<K,bNoDuplicates,Pr,A> Myt_;
 44     typedef std::vector<K,A>        Cont;
 45     typedef Cont::allocator_type    allocator_type;
 46     typedef Cont::size_type            size_type;
 47     typedef Cont::difference_type    difference_type;
 48     typedef Cont::reference            reference;
 49     typedef Cont::const_reference    const_reference;
 50     typedef Cont::value_type        value_type;
 51     typedef K                        key_type;
 52     typedef Cont::iterator            iterator;
 53     typedef Cont::const_iterator    const_iterator;
 54     typedef Pr                        key_compare;
 55     typedef Pr                        value_compare;
 56 
 57     typedef Cont::const_reverse_iterator
 58                                     const_reverse_iterator;
 59     typedef Cont::reverse_iterator    reverse_iterator;
 60 
 61     typedef std::pair<iterator, iterator> Pairii_;
 62     typedef std::pair<const_iterator, const_iterator> Paircc_;
 63     typedef std::pair<iterator, bool> Pairib_;
 64     explicit sorted_vector(const Pr& pred = Pr(),const A& al = A())
 65         :key_compare_(pred),vec_(al){}
 66 #if (_MSC_VER >= 1300)
 67     template<class It>
 68     sorted_vector(It first, It beyond, 
 69                     const Pr& pred = Pr(),const A& al = A())
 70         :key_compare_(pred),vec_(first,beyond,al)
 71         {stable_sort();}
 72 #else
 73     sorted_vector(const_iterator first, const_iterator beyond, 
 74                     const Pr& pred = Pr(),const A& al = A())
 75         :key_compare_(pred),vec_(first,beyond,al)
 76         {stable_sort();}
 77 #endif
 78     sorted_vector(const Myt_& x)
 79         : vec_(x.vec_),key_compare_(x.key_compare_)
 80         {}
 81     ~sorted_vector()                {}
 82     Myt_& operator=(const Myt_& x) {vec_.operator=(x.vec_);
 83                                      key_compare_= x.key_compare_;
 84                                      return *this;}
 85     Myt_& operator=(const Cont& x){vec_.operator=(x);
 86                                     sort();return *this;}
 87         
 88     void                reserve(size_type n)    {vec_.reserve(n);}
 89     iterator            begin()                    {return vec_.begin(); }
 90     const_iterator        begin() const            {return vec_.begin(); }
 91     iterator            end()                    {return vec_.end();}
 92     const_iterator        end() const                {return vec_.end();}
 93     reverse_iterator    rbegin()                {return vec_.rbegin();}
 94     const_reverse_iterator rbegin() const   
 95                                                 {return vec_.rbegin();}
 96 
 97     reverse_iterator rend()                        {return vec_.rend();}
 98     const_reverse_iterator rend() const     
 99                                                 {return vec_.rend();}
100 
101 
102     size_type size() const                        {return vec_.size();}
103     size_type max_size() const                    {return vec_.max_size();}
104     bool empty() const                            {return vec_.empty();}
105     A get_allocator() const                        {return vec_.get_allocator();}
106     const_reference at(size_type p) const        {return vec_.at(p);}
107     reference at(size_type p)                    {return vec_.at(p);}
108     const_reference operator[](size_type p) const
109                                                 {return vec_.operator[](p);}
110         
111     reference operator[](size_type p)            {return vec_.operator[](p);}
112     reference front()                            {return vec_.front();}
113     const_reference front() const                {return vec_.front();}
114     reference back()                            {return vec_.back();}
115     const_reference back() const                {return vec_.back();}
116     void pop_back()                                {vec_.pop_back();}
117 
118     void assign(const_iterator first, const_iterator beyond)                    
119                                                 {vec_.assign(first,beyond);}
120     void assign(size_type n, const K& x = K())
121                                                 {vec_.assign(n,x);}
122 /*insert members*/
123    Pairib_ insert(const value_type& x)
124         {
125             if(bNoDuplicates){
126                 iterator p= lower_bound(x);
127                 if(p==end()||key_compare_(x,*p)){
128                     return Pairib_(InsertImpl_(p,x),true);
129                 }else{
130                     return Pairib_(p,false);
131                 }
132             }else{
133                 iterator p= upper_bound(x);
134                 return Pairib_(InsertImpl_(p,x),true);
135             }
136         }
137    iterator insert(iterator it, const value_type& x)//it is the hint
138         {
139            if(it!=end() ){
140                if(bNoDuplicates){
141                    if(key_compare_(*it,x)){
142                        if((it+1)==end()||KeyCompare_Gt_(*(it+1),x)){//use hint
143                             return InsertImpl_(it+1,x);
144                        }else if(KeyCompare_Geq_(*(it+1),x)){
145                            return end();
146                        }
147                     }
148                }else{
149                    if(    KeyCompare_Leq_(*it,x)
150                        &&((it+1)==end()||KeyCompare_Geq_(*(it+1),x))){
151                        return InsertImpl_(it+1,x);
152                    }
153                }
154            }
155            return insert(x).first;
156         }
157 #if (_MSC_VER >= 1300)
158   template<class It>
159     void insert(It first, It beyond)
160     {
161         size_type n= std::distance(first,beyond);
162         reserve(size()+n);
163         for( ;first!=beyond;++first){
164             insert(*first);
165         }
166     }
167 #else
168    void insert(const_iterator first, const_iterator beyond)
169         {
170             size_type n= std::distance(first,beyond);
171             reserve(size()+n);
172             for( ;first!=beyond;++first){
173                 insert(*first);
174             }
175         }
176 #endif
177     iterator erase(iterator p)          {return vec_.erase(p);}
178     iterator erase(iterator first, iterator beyond)
179                                         {return vec_.erase(first,beyond);}
180     size_type erase(const K& key)     
181         {
182             Pairii_ begEnd= equal_range(key);
183             size_type n= std::distance(begEnd.first,begEnd.second);
184             erase(begEnd.first,begEnd.second);
185             return n;
186         }
187     void clear()                        {return vec_.clear();}
188         
189     bool Eq_(const Myt_& x) const      
190         {return (size() == x.size()
191         && std::equal(begin(), end(), x.begin())); }
192     bool Lt_(const Myt_& x) const
193         {return (std::lexicographical_compare(begin(), end(),
194                                         x.begin(), x.end()));}
195     void swap(Myt_& x)
196         {vec_.swap(x.vec_);std::swap(key_compare_,x.key_compare_);}
197         
198     friend void swap(Myt_& x, Myt_& Y_)
199         {x.swap(Y_); }
200 
201     key_compare key_comp() const            {return key_compare_; }
202     value_compare value_comp() const        {return (key_comp()); }
203     iterator find(const K& k)
204         {    iterator p = lower_bound(k);
205             return (p==end()||key_compare_(k, *p))? end():p;
206         }
207     const_iterator find(const K& k) const
208         {const_iterator p = lower_bound(k);
209         return (p==end()||key_compare_(k,*p))?end():p;}
210     size_type count(const K& k) const
211         {Paircc_ Ans_ = equal_range(k);
212         size_type n = std::distance(Ans_.first, Ans_.second);
213         return (n); }
214     iterator lower_bound(const K& k)
215         {return std::lower_bound(begin(), end(), k, key_compare_); }
216     const_iterator lower_bound(const K& k) const
217         {return std::lower_bound(begin(), end(), k, key_compare_); }
218     iterator upper_bound(const K& k)
219         {return std::upper_bound(begin(), end(), k, key_compare_); }
220     const_iterator upper_bound(const K& k) const
221         {return std::upper_bound(begin(), end(), k, key_compare_); }
222     Pairii_ equal_range(const K& k)
223         {return std::equal_range(begin(), end(), k, key_compare_); }
224     Paircc_ equal_range(const K& k) const
225         {return std::equal_range(begin(), end(), k, key_compare_); }
226 
227 /*functions for use with direct std::vector-access*/
228     Cont& get_container()
229         {return vec_;}
230     void sort()//restore sorted order after low level access 
231         {   std::sort(vec_.begin(),vec_.end(),key_compare_);
232             if( bNoDuplicates ){
233                 vec_.erase(Unique_(),vec_.end());
234             }
235         }
236     void stable_sort()//restore sorted order after low level access 
237         {   std::stable_sort(vec_.begin(),vec_.end(),key_compare_);
238             if( bNoDuplicates ){
239                 erase(Unique_(),end());
240             }
241         }   
242 protected:
243     iterator Unique_()
244         {   iterator front_= vec_.begin(),out_= vec_.end(),end_=vec_.end();
245             bool bCopy_= false;
246             for(iterator prev_; (prev_=front_)!=end_ && ++front_!=end_; ){
247                 if( key_compare_(*prev_,*front_)){
248                     if(bCopy_){
249                         *out_= *front_;
250                         out_++;
251                     }
252                 }else{
253                     if(!bCopy_){out_=front_;bCopy_=true;}
254                 }
255             }
256             return out_;
257         }
258     iterator InsertImpl_(iterator p,const value_type& x)
259         {return vec_.insert(p,x);}
260     bool KeyCompare_Leq_(const K& ty0,const K& ty1)
261         {return !key_compare_(ty1,ty0);}
262     bool KeyCompare_Geq_(const K& ty0,const K& ty1)
263         {return !key_compare_(ty0,ty1);}
264     bool KeyCompare_Gt_(const K& ty0,const K& ty1)
265         {return key_compare_(ty1,ty0);}
266 
267     key_compare         key_compare_;
268     Cont                vec_;
269 };
270 
271 
272 template<class K,bool bNoDuplicates,class Pr, class A> inline
273     bool operator==(const sorted_vector<K, bNoDuplicates,Pr,A>& x,
274                     const sorted_vector<K, bNoDuplicates,Pr,A>& Y_)
275     {return x.Eq_(Y_); }
276 template<class K,bool bNoDuplicates,class Pr, class A> inline
277     bool operator!=(const sorted_vector<K, bNoDuplicates,Pr,A>& x,
278                     const sorted_vector<K, bNoDuplicates,Pr,A>& Y_)
279     {return !(x == Y_); }
280 template<class K,bool bNoDuplicates,class Pr, class A> inline
281     bool operator<(const sorted_vector<K, bNoDuplicates,Pr,A>& x,
282                     const sorted_vector<K, bNoDuplicates,Pr,A>& Y_)
283     {return x.Lt_(Y_);}
284 template<class K,bool bNoDuplicates,class Pr,class A> inline
285     bool operator>(const sorted_vector<K, bNoDuplicates,Pr,A>& x,
286                     const sorted_vector<K, bNoDuplicates,Pr,A>& Y_)
287     {return Y_ < x; }
288 template<class K,bool bNoDuplicates,class Pr, class A> inline
289     bool operator<=(const sorted_vector<K, bNoDuplicates,Pr,A>& x,
290                     const sorted_vector<K, bNoDuplicates,Pr,A>& Y_)
291     {return !(Y_ < x); }
292 template<class K, bool bNoDuplicates,class Pr,class A> inline
293     bool operator>=(const sorted_vector<K, bNoDuplicates,Pr,A>& x,
294                     const sorted_vector<K, bNoDuplicates,Pr,A>& Y_)
295     {return (!(x < Y_)); }
296 }
297 #pragma warning(pop)
298 #pragma pack(pop)
299 #elif VERSION_SORTED_VECTOR_ != 0x00010010
300 #error You have included two sorted_vector.h with different version numbers
301 #endif

 

[转]An STL compliant sorted vector-源码示例

标签:

原文地址:http://www.cnblogs.com/scw2901/p/4285506.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!