📄 chashtable.h
字号:
/*____________________________________________________________________________
Copyright (C) 2002 PGP Corporation
All rights reserved.
$Id: CHashTable.h,v 1.4 2002/08/06 20:10:37 dallen Exp $
____________________________________________________________________________*/
#ifndef Included_CHashTable_h // [
#define Included_CHashTable_h
#include "pgpClassesConfig.h"
#include "CArray.h"
#include "CErrorState.h"
#include "CList.h"
_PGP_BEGIN
// Class CHashTable
template <typename T> class CHashTable SMART_ERROR_INHERIT
{
private:
struct HashTablePair : public CListableObject<HashTablePair>
{
PGPUInt32 key;
T *pItem;
};
public:
CHashTable(PGPUInt32 size);
~CHashTable();
PGPUInt32 Population() const {mPopulation;}
PGPUInt32 Size() const {return mSize;}
T * Lookup(PGPUInt32 key) const;
SMART_ERROR Add(PGPUInt32 key, T *pItem);
void Remove(PGPUInt32 key);
void Empty();
private:
CArray< CList<HashTablePair> * > mTable;
PGPUInt32 mSize;
PGPUInt32 mPopulation;
PGPUInt32 Hash(PGPUInt32 key) const;
HashTablePair * FindPairInList(PGPUInt32 i, PGPUInt32 key) const;
};
// CHashTable template member functions
template <typename T>
CHashTable<T>::CHashTable(PGPUInt32 size) :
mTable(size), mSize(size), mPopulation(0)
{
#if PGP_EXCEPTIONS
mTable.Wipe();
#else // !PGP_EXCEPTIONS
Status() = mTable.Status();
if (Status().IsntError())
mTable.Wipe();
#endif // !PGP_EXCEPTIONS
}
template <typename T>
CHashTable<T>::~CHashTable()
{
Empty();
}
template <typename T>
T *
CHashTable<T>::Lookup(PGPUInt32 key) const
{
PGPUInt32 i = Hash(key);
if (IsNull(mTable[i]))
return NULL;
HashTablePair *pPair = FindPairInList(i, key);
if (IsNull(pPair))
return NULL;
else
return pPair->pItem;
}
template <typename T>
SMART_ERROR
CHashTable<T>::Add(PGPUInt32 key, T *pItem)
{
pgpAssert(IsNull(Lookup(key)));
SMART_ERROR_DECLARE
PGPUInt32 i = Hash(key);
if (IsNull(mTable[i]))
mTable[i] = new CList<HashTablePair>;
#if PGP_EXCEPTIONS
try
{
HashTablePair *pPair = new HashTablePair;
pPair->key = key;
pPair->pItem = pItem;
mTable[i]->AddTail(pPair);
}
catch (CComboError&)
{
delete mTable[i];
mTable[i] = NULL;
throw;
}
#else // !PGP_EXCEPTIONS
if (IsNull(mTable[i]))
error.pgpErr = kPGPError_OutOfMemory;
if (error.IsntError())
{
HashTablePair *pPair = new HashTablePair;
if (IsNull(pPair))
error.pgpErr = kPGPError_OutOfMemory;
if (error.IsntError())
{
pPair->key = key;
pPair->pItem = pItem;
mTable[i]->AddTail(pPair);
}
if (error.IsError())
{
delete mTable[i];
mTable[i] = NULL;
}
}
#endif // PGP_EXCEPTIONS
SMART_ERROR_RETURN
}
template <typename T>
void
CHashTable<T>::Empty()
{
for (PGPUInt32 i = 0; i < Size(); i++)
{
if (IsntNull(mTable[i]))
{
mTable[i]->EmptyWithDelete();
delete mTable[i];
mTable[i] = NULL;
}
}
}
template <typename T>
void
CHashTable<T>::Remove(PGPUInt32 key)
{
pgpAssert(IsntNull(Lookup(key)));
PGPUInt32 i = Hash(key);
HashTablePair *pPair = FindPairInList(i, key);
mTable[i]->Remove(pPair);
delete pPair;
if (mTable[i]->IsEmpty())
{
delete mTable[i];
mTable[i] = NULL;
}
}
template <typename T>
PGPUInt32
CHashTable<T>::Hash(PGPUInt32 key) const
{
return ((key >> 4) % (Size() - 1));
}
template <typename T>
CHashTable<T>::HashTablePair *
CHashTable<T>::FindPairInList(PGPUInt32 i, PGPUInt32 key) const
{
HashTablePair *pPair = mTable[i]->Head();
while (IsntNull(pPair))
{
if (pPair->key == key)
break;
pPair = mTable[i]->Next(pPair);
}
return pPair;
}
_PGP_END
#endif // ] Included_CHashTable_h
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -