smallvec_type.hpp

Go to the documentation of this file.
00001 /* $Id: smallvec_type.hpp 17541 2009-09-14 20:59:46Z frosch $ */
00002 
00003 /*
00004  * This file is part of OpenTTD.
00005  * OpenTTD is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, version 2.
00006  * OpenTTD is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
00007  * See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with OpenTTD. If not, see <http://www.gnu.org/licenses/>.
00008  */
00009 
00012 #ifndef SMALLVEC_TYPE_HPP
00013 #define SMALLVEC_TYPE_HPP
00014 
00015 #include "alloc_func.hpp"
00016 #include "math_func.hpp"
00017 
00028 template <typename T, uint S>
00029 class SmallVector {
00030 protected:
00031   T *data;       
00032   uint items;    
00033   uint capacity; 
00034 
00035 public:
00036   SmallVector() : data(NULL), items(0), capacity(0) { }
00037 
00038   ~SmallVector()
00039   {
00040     free(this->data);
00041   }
00042 
00046   FORCEINLINE void Clear()
00047   {
00048     /* In fact we just reset the item counter avoiding the need to
00049      * probably reallocate the same amount of memory the list was
00050      * previously using. */
00051     this->items = 0;
00052   }
00053 
00057   void Reset()
00058   {
00059     this->items = 0;
00060     this->capacity = 0;
00061     free(data);
00062     data = NULL;
00063   }
00064 
00068   FORCEINLINE void Compact()
00069   {
00070     uint capacity = Align(this->items, S);
00071     if (capacity >= this->capacity) return;
00072 
00073     this->capacity = capacity;
00074     this->data = ReallocT(this->data, this->capacity);
00075   }
00076 
00080   FORCEINLINE T *Append()
00081   {
00082     if (this->items == this->capacity) {
00083       this->capacity += S;
00084       this->data = ReallocT(this->data, this->capacity);
00085     }
00086 
00087     return &this->data[this->items++];
00088   }
00089 
00096   FORCEINLINE const T *Find(const T &item) const
00097   {
00098     const T *pos = this->Begin();
00099     const T *end = this->End();
00100     while (pos != end && *pos != item) pos++;
00101     return pos;
00102   }
00103 
00110   FORCEINLINE T *Find(const T &item)
00111   {
00112     T *pos = this->Begin();
00113     const T *end = this->End();
00114     while (pos != end && *pos != item) pos++;
00115     return pos;
00116   }
00117 
00124   FORCEINLINE int FindIndex(const T &item)
00125   {
00126     int index = 0;
00127     T *pos = this->Begin();
00128     const T *end = this->End();
00129     while (pos != end && *pos != item) {
00130       pos++;
00131       index++;
00132     }
00133     return pos == end ? -1 : index;
00134   }
00135 
00142   FORCEINLINE bool Contains(const T &item) const
00143   {
00144     return this->Find(item) != this->End();
00145   }
00146 
00151   FORCEINLINE void Erase(T *item)
00152   {
00153     assert(item >= this->Begin() && item < this->End());
00154     *item = this->data[--this->items];
00155   }
00156 
00163   FORCEINLINE bool Include(const T &item)
00164   {
00165     bool is_member = this->Contains(item);
00166     if (!is_member) *this->Append() = item;
00167     return is_member;
00168   }
00169 
00173   FORCEINLINE uint Length() const
00174   {
00175     return this->items;
00176   }
00177 
00183   FORCEINLINE const T *Begin() const
00184   {
00185     return this->data;
00186   }
00187 
00193   FORCEINLINE T *Begin()
00194   {
00195     return this->data;
00196   }
00197 
00203   FORCEINLINE const T *End() const
00204   {
00205     return &this->data[this->items];
00206   }
00207 
00213   FORCEINLINE T *End()
00214   {
00215     return &this->data[this->items];
00216   }
00217 
00224   FORCEINLINE const T *Get(uint index) const
00225   {
00226     return &this->data[index];
00227   }
00228 
00235   FORCEINLINE T *Get(uint index)
00236   {
00237     return &this->data[index];
00238   }
00239 
00246   FORCEINLINE const T &operator[](uint index) const
00247   {
00248     return this->data[index];
00249   }
00250 
00257   FORCEINLINE T &operator[](uint index)
00258   {
00259     return this->data[index];
00260   }
00261 };
00262 
00263 
00274 template <typename T, uint S>
00275 class AutoFreeSmallVector : public SmallVector<T, S> {
00276 public:
00277   ~AutoFreeSmallVector()
00278   {
00279     this->Clear();
00280   }
00281 
00285   FORCEINLINE void Clear()
00286   {
00287     for (uint i = 0; i < this->items; i++) {
00288       free(this->data[i]);
00289     }
00290 
00291     this->items = 0;
00292   }
00293 };
00294 
00295 typedef AutoFreeSmallVector<char*, 4> StringList;
00296 
00297 #endif /* SMALLVEC_TYPE_HPP */

Generated on Wed Dec 23 23:27:49 2009 for OpenTTD by  doxygen 1.5.6