1 ///////////////////////////////////////////////////////////////////////////////
3 // Purpose: implementation of wxBaseArray class
4 // Author: Vadim Zeitlin
8 // Copyright: (c) 1998 Vadim Zeitlin <zeitlin@dptmaths.ens-cachan.fr>
9 // Licence: wxWindows license
10 ///////////////////////////////////////////////////////////////////////////////
12 // ============================================================================
14 // ============================================================================
17 #pragma implementation "dynarray.h"
20 #include "wx/wxprec.h"
26 #include "wx/dynarray.h"
30 #include <string.h> // for memmove
33 #define max(a, b) (((a) > (b)) ? (a) : (b))
36 // ============================================================================
38 // ============================================================================
40 // size increment = max(50% of current size, ARRAY_MAXSIZE_INCREMENT)
41 #define ARRAY_MAXSIZE_INCREMENT 4096
43 // ============================================================================
45 // ============================================================================
47 // ----------------------------------------------------------------------------
48 // wxBaseArray - dynamice array of 'long's
49 // ----------------------------------------------------------------------------
52 wxBaseArray::wxBaseArray()
56 m_pItems
= (long *) NULL
;
60 wxBaseArray::wxBaseArray(const wxBaseArray
& src
)
62 m_nSize
= // not src.m_nSize to save memory
63 m_nCount
= src
.m_nCount
;
66 m_pItems
= new long[m_nSize
];
67 memcpy(m_pItems
, src
.m_pItems
, m_nCount
*sizeof(long));
70 m_pItems
= (long *) NULL
;
73 // assignment operator
74 wxBaseArray
& wxBaseArray::operator=(const wxBaseArray
& src
)
85 m_nSize
= // not src.m_nSize to save memory
86 m_nCount
= src
.m_nCount
;
89 m_pItems
= new long[m_nSize
];
90 memcpy(m_pItems
, src
.m_pItems
, m_nCount
*sizeof(long));
93 m_pItems
= (long *) NULL
;
99 void wxBaseArray::Grow()
101 // only do it if no more place
102 if( m_nCount
== m_nSize
) {
104 // was empty, alloc some memory
105 m_nSize
= WX_ARRAY_DEFAULT_INITIAL_SIZE
;
106 m_pItems
= new long[m_nSize
];
110 // add 50% but not too much
111 size_t nIncrement
= m_nSize
< WX_ARRAY_DEFAULT_INITIAL_SIZE
112 ? WX_ARRAY_DEFAULT_INITIAL_SIZE
: m_nSize
>> 1;
113 if ( nIncrement
> ARRAY_MAXSIZE_INCREMENT
)
114 nIncrement
= ARRAY_MAXSIZE_INCREMENT
;
115 m_nSize
+= nIncrement
;
116 long *pNew
= new long[m_nSize
];
118 // copy data to new location
119 memcpy(pNew
, m_pItems
, m_nCount
*sizeof(long));
127 wxBaseArray::~wxBaseArray()
133 void wxBaseArray::Clear()
141 // pre-allocates memory (frees the previous data!)
142 void wxBaseArray::Alloc(size_t nSize
)
144 // only if old buffer was not big enough
145 if ( nSize
> m_nSize
) {
147 m_pItems
= new long[nSize
];
154 // minimizes the memory usage by freeing unused memory
155 void wxBaseArray::Shrink()
157 // only do it if we have some memory to free
158 if( m_nCount
< m_nSize
) {
159 // allocates exactly as much memory as we need
160 long *pNew
= new long[m_nCount
];
162 // copy data to new location
163 memcpy(pNew
, m_pItems
, m_nCount
*sizeof(long));
169 // searches the array for an item (forward or backwards)
170 int wxBaseArray::Index(long lItem
, bool bFromEnd
) const
173 if ( m_nCount
> 0 ) {
176 if ( m_pItems
[--n
] == lItem
)
183 for( size_t n
= 0; n
< m_nCount
; n
++ ) {
184 if( m_pItems
[n
] == lItem
)
192 // search for an item in a sorted array (binary search)
193 int wxBaseArray::Index(long lItem
, CMPFUNC fnCompare
) const
203 res
= (*fnCompare
)((const void *)lItem
, (const void *)m_pItems
[i
]);
214 // add item at the end
215 void wxBaseArray::Add(long lItem
)
218 m_pItems
[m_nCount
++] = lItem
;
221 // add item assuming the array is sorted with fnCompare function
222 void wxBaseArray::Add(long lItem
, CMPFUNC fnCompare
)
232 res
= (*fnCompare
)((const void *)lItem
, (const void *)m_pItems
[i
]);
243 wxASSERT( lo
== hi
); // I hope I got binary search right :-)
248 // add item at the given position
249 void wxBaseArray::Insert(long lItem
, size_t nIndex
)
251 wxCHECK_RET( nIndex
<= m_nCount
, wxT("bad index in wxArray::Insert") );
255 memmove(&m_pItems
[nIndex
+ 1], &m_pItems
[nIndex
],
256 (m_nCount
- nIndex
)*sizeof(long));
257 m_pItems
[nIndex
] = lItem
;
261 // removes item from array (by index)
262 void wxBaseArray::RemoveAt(size_t nIndex
)
264 wxCHECK_RET( nIndex
<= m_nCount
, wxT("bad index in wxArray::RemoveAt") );
266 memmove(&m_pItems
[nIndex
], &m_pItems
[nIndex
+ 1],
267 (m_nCount
- nIndex
- 1)*sizeof(long));
271 // removes item from array (by value)
272 void wxBaseArray::Remove(long lItem
)
274 int iIndex
= Index(lItem
);
276 wxCHECK_RET( iIndex
!= wxNOT_FOUND
,
277 wxT("removing inexistent item in wxArray::Remove") );
279 RemoveAt((size_t)iIndex
);
282 // sort array elements using passed comparaison function
283 void wxBaseArray::Sort(CMPFUNC fCmp
)
285 qsort(m_pItems
, m_nCount
, sizeof(long), fCmp
);