Haven't written a C + + plan for a long time. Nothing is to imitate after the STL, although not up to the standard STL program. But the simple function to implement.
STL In fact, deep: generic Programming, containers, algorithms, adapters ... There is some content to learn. The following is based on the STL source code. Write a very easy vector that implements part of the interface. In fact, vectors are relatively easy containers, and elements are arranged in memory in a row, with just three pointers to achieve very many interfaces. The other is the allocation of memory, which uses a allocator configurator provided by C + +. So the allocation is quite simple, the SGI version of the STL configuration in order to achieve the ultimate efficiency, the use of another allocator. Quite complicated. There's no writing here.
#ifndef __myvector_h__#define __myvector_h__template <class t>class Vector {public:typedef T value_type;typedef value_type* iterator;//Vector iterator is the native pointer typedef value_type* POINTER;TYPEDEF value_type& reference;typedef size_t Size_type;public:vector (): Start (null), Finish (null), end_of_storage (null) {}vector (size_type N, const value_type &value) {start = Alloc.allocate (n); end_of_storage = finish = start + n;uninitialized_fill_n (start, n, value);} Vector (size_type N) {start = Alloc.allocate (n); end_of_storage = finish = start + n;uninitialized_fill_n (Start, N, value_ty PE ());} ~vector () {//Sequence call element's destructor for (iterator i = start; I! = finish; ++i) Alloc.destroy (i);//Destroy Allocated space if (start! = NULL) Alloc.deall Ocate (start, end_of_storage-start);} Iterator begin () const{return start;} Iterator End () Const{return finish;} Size_type size () Const{return end ()-Begin ();//Use interface function, better wrapping}size_type capacity () Const{return end_of_storage-begin (); Use an interface function. Better wrapping}bool empty () Const{return begin () = = End();} The returned reference can be modified reference front () {return * (begin ());} The returned reference can be changed reference back () {return * (end ()-1);} Reference operator[] (const size_type N) {return * (begin () + N);} Const reference operator[] (const size_type N) Const{return * (begin () + N);} void push_back (const value_type &value) {if (finish = = End_of_storage) reallocate ();//Storage space is full. Then allocate memory alloc.construct (finish, value); ++finish;} void reallocate (); void Pop_back () {--finish;alloc.destroy (finish);//destructors the last function, but does not free space}//clears an element iterator erase ( Iterator position) {if (position + 1! = finish) Copy (position + 1, finish, position);--finish;alloc.destroy (finish); return Position;} Clears an element iterator erase (iterator first, iterator last) {if (First < start | | Last > Finish) throw exception ("Invalid I Nput. "); Copy (last, finish, first); int len = Last-first;while (len--) Alloc.destroy (--finish); return first;} void Clear () {Erase (Begin (), end ());} Private:iterator start;iterator finish;iterator end_of_storage;private:static std::allocator<value_type&Gt alloc;//Space Configurator. Use static properties to save space};template <class type>std::allocator<type> vector<type>::alloc;template <class Type >void vector<type>::reallocate () {Size_type oldsize = size (); Size_type newsize = 2 * (oldsize = = 0? 1:oldsize); Allocate new memory space iterator Newstart = Alloc.allocate (newsize); Uninitialized_copy (start, Finish, Newstart);// The destructor for each element in order is called for (iterator i = start; I! = finish; ++i) Alloc.destroy (i);//destroys allocated space before destroying the primary check for Nullif (start! = NULL) alloc . deallocate (Start, end_of_storage-start);//update subscript start = Newstart;finish = start + oldsize;end_of_storage = start + newsi Ze;} #endif
Insert operation should be considered as the most complex interface, design to the element of the move, (possibly) another allocation of memory, and so on, here I just implemented a simple form:
Template <class type>void Vector<type>::insert (iterator position, const value_type &value) {Size_type diff = position-start;if (finish = end_of_storage) reallocate ();p osition = start + diff;//Note that copy is not available here. Since the final location of the destination has not yet been constructed,//assignment involves a destructor, a destructor for an object that is not constructed, the behavior is undefined alloc.construct (finish, * (finish-1)); ++finish;copy_backward ( Position, finish-1, finish);//cannot use uninitialized_copy. Since this function is constructed from the front to back. This will result in overwriting//uninitialized_copy (position, finish, position + 1);//Insert new object, Direct assignment can be *position = value;}
Test procedure:
int main () {vector<int> v;v.push_back (1); cout << "size =" << v.size () << endl;cout << "Capac ity = "<< v.capacity () << endl;v.push_back (2); cout <<" size = "<< v.size () << endl;cout &L t;< "capacity =" << v.capacity () << endl;v.push_back (3); cout << "size =" << v.size () << Endl;cout << "capacity =" << v.capacity () << endl;v.push_back (4); cout << "size =" << v.si Ze () << endl;cout << "capacity =" << v.capacity () << endl;v.push_back (5); cout << "size =" << v.size () << endl;cout << "capacity =" << v.capacity () << Endl; Vector<int>::iterator iter1 = V.begin (); Vector<int>::iterator iter2 = iter1 + 3;v.erase (iter1, iter2); cout << "size =" << v.size () << End L;cout << "capacity =" << v.capacity () << endl;v.clear (); cout << "size =" << v.size () < < Endl;cout << "capacity =" << v.capacity () << endl;v.push_back (123); cout << "size =" << v. Size () << endl;cout << "capacity =" << v.capacity () << endl;for (Vector<int>::iterator iter = V.begin (); Iter! = V.end (); ++iter) cout << *iter << endl;system ("pause"); return 0;}
Execution Result:
References:
Anatomy of STL Source code
"C + + Primer"
Copyright notice: This article blog original article. Blogs, without consent, may not be reproduced.
C + + Easy vector