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

原文地址: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 ([email protected]). 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 [email protected]
 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
时间: 2024-10-16 12:16:49

[转]An STL compliant sorted vector-源码示例的相关文章

vector源码(参考STL源码--侯捷)-----空间分配导致迭代器失效

vector源码1(参考STL源码--侯捷) vector源码2(参考STL源码--侯捷) #include<bits/stdc++.h> using namespace std; int main(){ vector<int> v(3,3); vector<int>::iterator it=v.begin(); cout<<v.size()<<" "<<v.capacity()<<endl;//3

vector源码2(参考STL源码--侯捷)

vector源码1(参考STL源码--侯捷) vector源码(参考STL源码--侯捷)-----空间分配导致迭代器失效 vector的构造和内存管理 vector所采用的数据结构非常简单:线性连续空间,它是由两个迭代器start和finish分别指向配置得来的连续空间中目前已被使用的范围,并以迭代器end_of_storage指向整块连续空间(含备用空间)的尾端: class vector //详细源码可见 { .......... protected: typedef simple_allo

vector源码1(参考STL源码--侯捷)

vector源码2(参考STL源码--侯捷) vector源码(参考STL源码--侯捷)-----空间分配导致迭代器失效 vector概述 Vector是动态空间,随着元素的加入,它的内部机制会自行扩充空间纳入新元素,vector的使用效率,关键在于其对大小的控制以及重新配置时的元素迁移效率. Vector定义摘要 template <class T,class Alloc=alloc>//alloc是SGI STL的空间配置器 class vector { public: typedef T

转:【Java集合源码剖析】Vector源码剖析

转载请注明出处:http://blog.csdn.net/ns_code/article/details/35793865   Vector简介 Vector也是基于数组实现的,是一个动态数组,其容量能自动增长. Vector是JDK1.0引入了,它的很多实现方法都加入了同步语句,因此是线程安全的(其实也只是相对安全,有些时候还是要加入同步语句来保证线程的安全),可以用于多线程环境. Vector没有丝线Serializable接口,因此它不支持序列化,实现了Cloneable接口,能被克隆,实

C++:浅谈c++资源管理以及对[STL]智能指针auto_ptr源码分析,左值与右值

C++:浅谈c++资源管理以及对[STL]智能指针auto_ptr源码分析 by 小威威 1. 知识引入 在C++编程中,动态分配的内存在使用完毕之后一般都要delete(释放),否则就会造成内存泄漏,导致不必要的后果.虽然大多数初学者都会有这样的意识,但是有些却不以为意.我曾问我的同学关于动态内存的分配与释放,他的回答是:"只要保证new和delete成对出现就行了.如果在构造函数中new(动态分配内存),那么在析构函数中delete(释放)就可以避免内存泄漏了!" 事实果真如此么?

【Java集合源码剖析】Vector源码剖析

转载请注明出处:http://blog.csdn.net/ns_code/article/details/35793865 Vector简介 Vector也是基于数组实现的,是一个动态数组,其容量能自动增长. LinkedList是JDK1.0引入了,它的很多实现方法都加入了同步语句,因此是线程安全的(其实也只是相对安全,有些时候还是要加入同步语句来保证线程的安全),可以用于多线程环境. LinkedList没有丝线Serializable接口,因此它不支持序列化,实现了Cloneable接口,

Vector 源码分析 jdk1.8

Vector简介 Vector 是矢量队列,它是JDK1.0版本添加的类.继承于AbstractList,实现了List, RandomAccess, Cloneable这些接口.Vector 继承了AbstractList,实现了List:所以,它是一个队列,支持相关的添加.删除.修改.遍历等功能.Vector 实现了RandmoAccess接口,即提供了随机访问功能.RandmoAccess是java中用来被List实现,为List提供快速访问功能的.在Vector中,我们即可以通过元素的序

Vector源码解析

概要 学完ArrayList和LinkedList之后,我们接着学习Vector.学习方式还是和之前一样,先对Vector有个整体认识,然后再学习它的源码:最后再通过实例来学会使用它.第1部分 Vector介绍第2部分 Vector数据结构第3部分 Vector源码解析(基于JDK1.6.0_45)第4部分 Vector遍历方式第5部分 Vector示例 转载请注明出处:http://www.cnblogs.com/skywang12345/p/3308833.html 第1部分 Vector介

Stack和Vector源码分析

Stack和Vector源码分析 Stack和Vector源码分析stack源码分析1.Stack是什么2.Stack的结构图3.Stack继承关系4.Stack的主要方法5.Stack源码Vector源码分析1.vector介绍2.vector的关系图3.vector和ArrayList的关系4.Vector的大致图像5.Vector的源码 stack源码分析 1.Stack是什么 Stack是栈.它的特性是:先进后出(FILO, First In Last Out). java工具包中的St