31 #include <AK/Tools/Common/AkArray.h>
32 #include <AK/Tools/Common/AkKeyDef.h>
36 template <
class T_KEY,
class T_ITEM,
class U_POOL = ArrayPoolDefault, AkUInt32 TGrowBy = 1,
class TMovePolicy = AkAssignmentMovePolicy<MapStruct<T_KEY, T_ITEM> > >
37 class CAkKeyArray :
public AkArray< MapStruct<T_KEY, T_ITEM>, const MapStruct<T_KEY, T_ITEM>&, U_POOL, TGrowBy, TMovePolicy>
47 return (it != this->
End()) ? &(it.pItem->item) : NULL;
55 T_ITEM *
Set(T_KEY in_Key,
const T_ITEM & in_Item)
57 T_ITEM* pSearchedItem =
Exists(in_Key);
60 *pSearchedItem = in_Item;
67 pStruct->
key = in_Key;
68 pStruct->
item = in_Item;
69 pSearchedItem = &(pStruct->
item);
75 T_ITEM *
SetFirst(T_KEY in_Key,
const T_ITEM & in_Item)
77 T_ITEM* pSearchedItem =
Exists(in_Key);
80 *pSearchedItem = in_Item;
87 pStruct->
key = in_Key;
88 pStruct->
item = in_Item;
89 pSearchedItem = &(pStruct->
item);
95 T_ITEM *
Set(T_KEY in_Key)
97 T_ITEM* pSearchedItem =
Exists(in_Key);
103 pStruct->
key = in_Key;
104 pSearchedItem = &(pStruct->
item);
107 return pSearchedItem;
118 for (; it != itEnd; ++it)
120 if ((*it).key == in_Item)
134 if (it != this->
End())
147 if (it != this->
End())
158 static AkForceInline T_KEY &
Get(T_ITEM & in_item)
168 template<
class THIS_CLASS>
169 static AkForceInline
bool Lesser(THIS_CLASS*, T_KEY &a, T_KEY &b)
174 template<
class THIS_CLASS>
175 static AkForceInline
bool Equal(THIS_CLASS*, T_KEY &a, T_KEY &b)
183 template <
class T_KEY,
class T_ITEM,
class U_POOL,
class U_KEY = AkGetArrayKey< T_KEY, T_ITEM >,
unsigned long TGrowBy = 1,
class TMovePolicy = AkAssignmentMovePolicy<T_ITEM>,
class TComparePolicy = AkDefaultSortedKeyCompare<T_KEY> >
187 AkForceInline
bool Lesser(T_KEY &a, T_KEY &b)
const
189 return TComparePolicy::Lesser((
void*)
this, a, b);
192 AkForceInline
bool Equal(T_KEY &a, T_KEY &b)
const
194 return TComparePolicy::Equal((
void*)
this, a, b);
201 return bFound ? pItem : NULL;
206 T_ITEM *
Add(T_KEY in_key)
212 U_KEY::Get(*pItem) = in_key;
225 unsigned int uIdx = (
unsigned int)(pItem - this->
m_pItems);
226 pItem = this->
Insert(uIdx);
238 T_ITEM *
Set(T_KEY in_key)
241 return Set(in_key, bFound);
244 T_ITEM *
Set(T_KEY in_key,
bool & out_bExists)
251 unsigned int uIdx = (
unsigned int)(pItem - this->
m_pItems);
252 pItem = this->
Insert(uIdx);
260 U_KEY::Get(*pItem) = in_key;
269 T_ITEM * pItem =
Exists(in_key);
283 void Reorder(T_KEY in_OldKey, T_KEY in_NewKey,
const T_ITEM & in_item)
291 unsigned int uIdx = (
unsigned int)(pItem - this->
m_pItems);
292 unsigned int uLastIdx = this->
Length() - 1;
294 AKASSERT(*pItem == in_item);
296 bool bNeedReordering =
false;
299 T_ITEM * pPrevItem = this->
m_pItems + (uIdx - 1);
300 if (
Lesser(in_NewKey, U_KEY::Get(*pPrevItem)))
305 T_ITEM * pSecondPrevItem = this->
m_pItems + (uIdx - 2);
306 if (
Lesser(U_KEY::Get(*pSecondPrevItem), in_NewKey))
308 return Swap(pPrevItem, pItem);
312 bNeedReordering =
true;
317 return Swap(pPrevItem, pItem);
321 if (!bNeedReordering && uIdx < uLastIdx)
323 T_ITEM * pNextItem = this->
m_pItems + (uIdx + 1);
324 if (
Lesser(U_KEY::Get(*pNextItem), in_NewKey))
327 if (uIdx < (uLastIdx - 1))
329 T_ITEM * pSecondNextItem = this->
m_pItems + (uIdx + 2);
330 if (
Lesser(in_NewKey, U_KEY::Get(*pSecondNextItem)))
332 return Swap(pNextItem, pItem);
336 bNeedReordering =
true;
341 return Swap(pNextItem, pItem);
351 unsigned int uIdxToInsert;
355 uIdxToInsert = (
unsigned int)(pTargetItem - this->
m_pItems);
356 if (uIdxToInsert > uIdx)
363 uIdxToInsert = uLastIdx;
366 T_ITEM * pStartItem = this->
m_pItems + uIdx;
367 T_ITEM * pEndItem = this->
m_pItems + uIdxToInsert;
368 if (uIdxToInsert < uIdx)
371 while (pStartItem != pEndItem)
374 pStartItem[1] = pStartItem[0];
380 while (pStartItem != pEndItem)
382 pStartItem[0] = pStartItem[1];
386 pEndItem[0] = in_item;
395 AkInt32 NumItemsToReInsert = this->
Length();
396 if (NumItemsToReInsert != 0)
400 T_ITEM * pReinsertionItem = this->
m_pItems;
402 for (AkInt32 idx = 0; idx < NumItemsToReInsert; ++idx)
404 T_ITEM ItemtoReinsert = pReinsertionItem[idx];
406 T_KEY keyToReinsert = U_KEY::Get(ItemtoReinsert);
408 T_ITEM* pInsertionEmplacement =
AddNoSetKey(keyToReinsert);
410 AKASSERT(pInsertionEmplacement);
411 *pInsertionEmplacement = ItemtoReinsert;
419 AkUInt32 uNumToSearch = this->
Length();
423 while ( uNumToSearch > 0 )
425 iPivot = iBase + ( uNumToSearch >> 1 );
426 T_KEY pivotKey = U_KEY::Get( this->
m_pItems[ iPivot ] );
427 if (
Equal( pivotKey, in_key ) )
433 if (
Lesser( pivotKey, in_key ) )
445 AkForceInline
void Swap(T_ITEM * in_ItemA, T_ITEM * in_ItemB)
447 T_ITEM ItemTemp = *in_ItemA;
448 *in_ItemA = *in_ItemB;
449 *in_ItemB = ItemTemp;
454 #endif //_KEYARRAY_H_