aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/libraries/ode-0.9/OPCODE/Ice/IceContainer.h
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--libraries/ode-0.9/OPCODE/Ice/IceContainer.h212
1 files changed, 212 insertions, 0 deletions
diff --git a/libraries/ode-0.9/OPCODE/Ice/IceContainer.h b/libraries/ode-0.9/OPCODE/Ice/IceContainer.h
new file mode 100644
index 0000000..d726c2a
--- /dev/null
+++ b/libraries/ode-0.9/OPCODE/Ice/IceContainer.h
@@ -0,0 +1,212 @@
1///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
2/**
3 * Contains a simple container class.
4 * \file IceContainer.h
5 * \author Pierre Terdiman
6 * \date February, 5, 2000
7 */
8///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
9
10///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
11// Include Guard
12#ifndef __ICECONTAINER_H__
13#define __ICECONTAINER_H__
14
15 #define CONTAINER_STATS
16
17 enum FindMode
18 {
19 FIND_CLAMP,
20 FIND_WRAP,
21
22 FIND_FORCE_DWORD = 0x7fffffff
23 };
24
25 class ICECORE_API Container
26 {
27 public:
28 // Constructor / Destructor
29 Container();
30 Container(const Container& object);
31 Container(udword size, float growth_factor);
32 ~Container();
33 // Management
34 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
35 /**
36 * A O(1) method to add a value in the container. The container is automatically resized if needed.
37 * The method is inline, not the resize. The call overhead happens on resizes only, which is not a problem since the resizing operation
38 * costs a lot more than the call overhead...
39 *
40 * \param entry [in] a udword to store in the container
41 * \see Add(float entry)
42 * \see Empty()
43 * \see Contains(udword entry)
44 * \return Self-Reference
45 */
46 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
47 inline_ Container& Add(udword entry)
48 {
49 // Resize if needed
50 if(mCurNbEntries==mMaxNbEntries) Resize();
51
52 // Add new entry
53 mEntries[mCurNbEntries++] = entry;
54 return *this;
55 }
56
57 inline_ Container& Add(const udword* entries, udword nb)
58 {
59 // Resize if needed
60 if(mCurNbEntries+nb>mMaxNbEntries) Resize(nb);
61
62 // Add new entry
63 CopyMemory(&mEntries[mCurNbEntries], entries, nb*sizeof(udword));
64 mCurNbEntries+=nb;
65 return *this;
66 }
67
68 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
69 /**
70 * A O(1) method to add a value in the container. The container is automatically resized if needed.
71 * The method is inline, not the resize. The call overhead happens on resizes only, which is not a problem since the resizing operation
72 * costs a lot more than the call overhead...
73 *
74 * \param entry [in] a float to store in the container
75 * \see Add(udword entry)
76 * \see Empty()
77 * \see Contains(udword entry)
78 * \return Self-Reference
79 */
80 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
81 inline_ Container& Add(float entry)
82 {
83 // Resize if needed
84 if(mCurNbEntries==mMaxNbEntries) Resize();
85
86 // Add new entry
87 mEntries[mCurNbEntries++] = IR(entry);
88 return *this;
89 }
90
91 inline_ Container& Add(const float* entries, udword nb)
92 {
93 // Resize if needed
94 if(mCurNbEntries+nb>mMaxNbEntries) Resize(nb);
95
96 // Add new entry
97 CopyMemory(&mEntries[mCurNbEntries], entries, nb*sizeof(float));
98 mCurNbEntries+=nb;
99 return *this;
100 }
101
102 //! Add unique [slow]
103 inline_ Container& AddUnique(udword entry)
104 {
105 if(!Contains(entry)) Add(entry);
106 return *this;
107 }
108
109 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
110 /**
111 * Clears the container. All stored values are deleted, and it frees used ram.
112 * \see Reset()
113 * \return Self-Reference
114 */
115 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
116 Container& Empty();
117
118 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
119 /**
120 * Resets the container. Stored values are discarded but the buffer is kept so that further calls don't need resizing again.
121 * That's a kind of temporal coherence.
122 * \see Empty()
123 */
124 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
125 inline_ void Reset()
126 {
127 // Avoid the write if possible
128 // ### CMOV
129 if(mCurNbEntries) mCurNbEntries = 0;
130 }
131
132 // HANDLE WITH CARE
133 inline_ void ForceSize(udword size)
134 {
135 mCurNbEntries = size;
136 }
137
138 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
139 /**
140 * Sets the initial size of the container. If it already contains something, it's discarded.
141 * \param nb [in] Number of entries
142 * \return true if success
143 */
144 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
145 bool SetSize(udword nb);
146
147 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
148 /**
149 * Refits the container and get rid of unused bytes.
150 * \return true if success
151 */
152 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
153 bool Refit();
154
155 // Checks whether the container already contains a given value.
156 bool Contains(udword entry, udword* location=null) const;
157 // Deletes an entry - doesn't preserve insertion order.
158 bool Delete(udword entry);
159 // Deletes an entry - does preserve insertion order.
160 bool DeleteKeepingOrder(udword entry);
161 //! Deletes the very last entry.
162 inline_ void DeleteLastEntry() { if(mCurNbEntries) mCurNbEntries--; }
163 //! Deletes the entry whose index is given
164 inline_ void DeleteIndex(udword index) { mEntries[index] = mEntries[--mCurNbEntries]; }
165
166 // Helpers
167 Container& FindNext(udword& entry, FindMode find_mode=FIND_CLAMP);
168 Container& FindPrev(udword& entry, FindMode find_mode=FIND_CLAMP);
169 // Data access.
170 inline_ udword GetNbEntries() const { return mCurNbEntries; } //!< Returns the current number of entries.
171 inline_ udword GetEntry(udword i) const { return mEntries[i]; } //!< Returns ith entry
172 inline_ udword* GetEntries() const { return mEntries; } //!< Returns the list of entries.
173
174 inline_ udword GetFirst() const { return mEntries[0]; }
175 inline_ udword GetLast() const { return mEntries[mCurNbEntries-1]; }
176
177 // Growth control
178 inline_ float GetGrowthFactor() const { return mGrowthFactor; } //!< Returns the growth factor
179 inline_ void SetGrowthFactor(float growth) { mGrowthFactor = growth; } //!< Sets the growth factor
180 inline_ bool IsFull() const { return mCurNbEntries==mMaxNbEntries; } //!< Checks the container is full
181 inline_ BOOL IsNotEmpty() const { return mCurNbEntries; } //!< Checks the container is empty
182
183 //! Read-access as an array
184 inline_ udword operator[](udword i) const { ASSERT(i>=0 && i<mCurNbEntries); return mEntries[i]; }
185 //! Write-access as an array
186 inline_ udword& operator[](udword i) { ASSERT(i>=0 && i<mCurNbEntries); return mEntries[i]; }
187
188 // Stats
189 udword GetUsedRam() const;
190
191 //! Operator for "Container A = Container B"
192 //void operator = (const Container& object);
193
194#ifdef CONTAINER_STATS
195 inline_ udword GetNbContainers() const { return mNbContainers; }
196 inline_ udword GetTotalBytes() const { return mUsedRam; }
197 private:
198
199 static udword mNbContainers; //!< Number of containers around
200 static udword mUsedRam; //!< Amount of bytes used by containers in the system
201#endif
202 private:
203 // Resizing
204 bool Resize(udword needed=1);
205 // Data
206 udword mMaxNbEntries; //!< Maximum possible number of entries
207 udword mCurNbEntries; //!< Current number of entries
208 udword* mEntries; //!< List of entries
209 float mGrowthFactor; //!< Resize: new number of entries = old number * mGrowthFactor
210 };
211
212#endif // __ICECONTAINER_H__