mirror of
https://github.com/0TheSpy/Seaside.git
synced 2025-01-07 10:03:29 +08:00
164 lines
3.2 KiB
C++
164 lines
3.2 KiB
C++
#ifndef UTLPRIORITYQUEUE_H
|
|
#define UTLPRIORITYQUEUE_H
|
|
#ifdef _WIN32
|
|
#pragma once
|
|
#endif
|
|
|
|
#include "utlvector.h"
|
|
|
|
template< class T >
|
|
class CUtlPriorityQueue
|
|
{
|
|
public:
|
|
typedef bool (*LessFunc_t)(T const&, T const&);
|
|
|
|
typedef T ElemType_t;
|
|
|
|
CUtlPriorityQueue(int growSize = 0, int initSize = 0, LessFunc_t lessfunc = 0);
|
|
CUtlPriorityQueue(T* pMemory, int numElements, LessFunc_t lessfunc = 0);
|
|
|
|
inline T const& ElementAtHead() const { return m_heap.Element(0); }
|
|
|
|
inline bool IsValidIndex(int index) { return m_heap.IsValidIndex(index); }
|
|
|
|
void RemoveAtHead();
|
|
void RemoveAt(int index);
|
|
|
|
void Insert(T const& element);
|
|
void SetLessFunc(LessFunc_t func);
|
|
|
|
inline int Count() const { return m_heap.Count(); }
|
|
|
|
void RemoveAll() { m_heap.RemoveAll(); }
|
|
|
|
void Purge() { m_heap.Purge(); }
|
|
|
|
inline const T& Element(int index) const { return m_heap.Element(index); }
|
|
|
|
protected:
|
|
CUtlVector<T> m_heap;
|
|
|
|
void Swap(int index1, int index2);
|
|
|
|
LessFunc_t m_LessFunc;
|
|
};
|
|
|
|
template< class T >
|
|
inline CUtlPriorityQueue<T>::CUtlPriorityQueue(int growSize, int initSize, LessFunc_t lessfunc) :
|
|
m_heap(growSize, initSize), m_LessFunc(lessfunc)
|
|
{
|
|
}
|
|
|
|
template< class T >
|
|
inline CUtlPriorityQueue<T>::CUtlPriorityQueue(T* pMemory, int numElements, LessFunc_t lessfunc) :
|
|
m_heap(pMemory, numElements), m_LessFunc(lessfunc)
|
|
{
|
|
}
|
|
|
|
template <class T>
|
|
void CUtlPriorityQueue<T>::RemoveAtHead()
|
|
{
|
|
m_heap.FastRemove(0);
|
|
int index = 0;
|
|
|
|
int count = Count();
|
|
if (!count)
|
|
return;
|
|
|
|
int half = count / 2;
|
|
int larger = index;
|
|
while (index < half)
|
|
{
|
|
int child = ((index + 1) * 2) - 1;
|
|
if (child < count)
|
|
{
|
|
if (m_LessFunc(m_heap[index], m_heap[child]))
|
|
{
|
|
larger = child;
|
|
}
|
|
}
|
|
child++;
|
|
if (child < count)
|
|
{
|
|
if (m_LessFunc(m_heap[larger], m_heap[child]))
|
|
larger = child;
|
|
}
|
|
|
|
if (larger == index)
|
|
break;
|
|
|
|
Swap(index, larger);
|
|
index = larger;
|
|
}
|
|
}
|
|
|
|
|
|
template <class T>
|
|
void CUtlPriorityQueue<T>::RemoveAt(int index)
|
|
{
|
|
Assert(m_heap.IsValidIndex(index));
|
|
m_heap.FastRemove(index);
|
|
|
|
int count = Count();
|
|
if (!count)
|
|
return;
|
|
|
|
int half = count / 2;
|
|
int larger = index;
|
|
while (index < half)
|
|
{
|
|
int child = ((index + 1) * 2) - 1;
|
|
if (child < count)
|
|
{
|
|
if (m_LessFunc(m_heap[index], m_heap[child]))
|
|
{
|
|
larger = child;
|
|
}
|
|
}
|
|
child++;
|
|
if (child < count)
|
|
{
|
|
if (m_LessFunc(m_heap[larger], m_heap[child]))
|
|
larger = child;
|
|
}
|
|
|
|
if (larger == index)
|
|
break;
|
|
|
|
Swap(index, larger);
|
|
index = larger;
|
|
}
|
|
}
|
|
|
|
template <class T>
|
|
void CUtlPriorityQueue<T>::Insert(T const& element)
|
|
{
|
|
int index = m_heap.AddToTail();
|
|
m_heap[index] = element;
|
|
|
|
while (index != 0)
|
|
{
|
|
int parent = ((index + 1) / 2) - 1;
|
|
if (m_LessFunc(m_heap[index], m_heap[parent]))
|
|
break;
|
|
|
|
Swap(parent, index);
|
|
index = parent;
|
|
}
|
|
}
|
|
|
|
template <class T>
|
|
void CUtlPriorityQueue<T>::Swap(int index1, int index2)
|
|
{
|
|
T tmp = m_heap[index1];
|
|
m_heap[index1] = m_heap[index2];
|
|
m_heap[index2] = tmp;
|
|
}
|
|
|
|
template <class T>
|
|
void CUtlPriorityQueue<T>::SetLessFunc(LessFunc_t lessfunc)
|
|
{
|
|
m_LessFunc = lessfunc;
|
|
}
|
|
|
|
#endif |