Wm4TStringHashTable.inl
Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017 namespace Wm4
00018 {
00019
00020 template <class TVALUE>
00021 TStringHashTable<TVALUE>::TStringHashTable (int iTableSize)
00022 {
00023 assert(iTableSize > 0);
00024
00025 m_iTableSize = iTableSize;
00026 m_iQuantity = 0;
00027 m_iIndex = 0;
00028 m_pkItem = 0;
00029 m_apkTable = WM4_NEW HashItem*[m_iTableSize];
00030 memset(m_apkTable,0,m_iTableSize*sizeof(HashItem*));
00031 }
00032
00033 template <class TVALUE>
00034 TStringHashTable<TVALUE>::~TStringHashTable ()
00035 {
00036 RemoveAll();
00037 WM4_DELETE[] m_apkTable;
00038 }
00039
00040 template <class TVALUE>
00041 int TStringHashTable<TVALUE>::GetQuantity () const
00042 {
00043 return m_iQuantity;
00044 }
00045
00046 template <class TVALUE>
00047 bool TStringHashTable<TVALUE>::Insert (const std::string& rkKey,
00048 const TVALUE& rtValue)
00049 {
00050
00051 int iIndex = HashFunction(rkKey);
00052 HashItem* pkItem = m_apkTable[iIndex];
00053
00054
00055 while (pkItem)
00056 {
00057 if (rkKey == pkItem->m_kKey)
00058 {
00059
00060 return false;
00061 }
00062 pkItem = pkItem->m_pkNext;
00063 }
00064
00065
00066 pkItem = WM4_NEW HashItem;
00067 pkItem->m_kKey = rkKey;
00068 pkItem->m_tValue = rtValue;
00069 pkItem->m_pkNext = m_apkTable[iIndex];
00070 m_apkTable[iIndex] = pkItem;
00071 m_iQuantity++;
00072
00073 return true;
00074 }
00075
00076 template <class TVALUE>
00077 TVALUE* TStringHashTable<TVALUE>::Find (const std::string& rkKey) const
00078 {
00079
00080 int iIndex = HashFunction(rkKey);
00081 HashItem* pkItem = m_apkTable[iIndex];
00082
00083
00084 while (pkItem)
00085 {
00086 if (rkKey == pkItem->m_kKey)
00087 {
00088
00089 return &pkItem->m_tValue;
00090 }
00091 pkItem = pkItem->m_pkNext;
00092 }
00093
00094 return 0;
00095 }
00096
00097 template <class TVALUE>
00098 bool TStringHashTable<TVALUE>::Remove (const std::string& rkKey)
00099 {
00100
00101 int iIndex = HashFunction(rkKey);
00102 HashItem* pkItem = m_apkTable[iIndex];
00103
00104 if (!pkItem)
00105 {
00106 return false;
00107 }
00108
00109 if (rkKey == pkItem->m_kKey)
00110 {
00111
00112 HashItem* pkSave = pkItem;
00113 m_apkTable[iIndex] = pkItem->m_pkNext;
00114 WM4_DELETE pkSave;
00115 m_iQuantity--;
00116 return true;
00117 }
00118
00119
00120 HashItem* pkPrev = pkItem;
00121 HashItem* pkCurr = pkItem->m_pkNext;
00122 while (pkCurr && rkKey != pkCurr->m_kKey)
00123 {
00124 pkPrev = pkCurr;
00125 pkCurr = pkCurr->m_pkNext;
00126 }
00127
00128 if (pkCurr)
00129 {
00130
00131 pkPrev->m_pkNext = pkCurr->m_pkNext;
00132 WM4_DELETE pkCurr;
00133 m_iQuantity--;
00134 return true;
00135 }
00136
00137 return false;
00138 }
00139
00140 template <class TVALUE>
00141 void TStringHashTable<TVALUE>::RemoveAll ()
00142 {
00143 if (m_iQuantity > 0)
00144 {
00145 for (int iIndex = 0; iIndex < m_iTableSize; iIndex++)
00146 {
00147 while (m_apkTable[iIndex])
00148 {
00149 HashItem* pkSave = m_apkTable[iIndex];
00150 m_apkTable[iIndex] = m_apkTable[iIndex]->m_pkNext;
00151 WM4_DELETE pkSave;
00152 if (--m_iQuantity == 0)
00153 {
00154 return;
00155 }
00156 }
00157 }
00158 }
00159 }
00160
00161 template <class TVALUE>
00162 TVALUE* TStringHashTable<TVALUE>::GetFirst (std::string* pkKey) const
00163 {
00164 if (m_iQuantity > 0)
00165 {
00166 for (m_iIndex = 0; m_iIndex < m_iTableSize; m_iIndex++)
00167 {
00168 if (m_apkTable[m_iIndex])
00169 {
00170 m_pkItem = m_apkTable[m_iIndex];
00171 *pkKey = m_pkItem->m_kKey;
00172 return &m_pkItem->m_tValue;
00173 }
00174 }
00175 }
00176
00177 return 0;
00178 }
00179
00180 template <class TVALUE>
00181 TVALUE* TStringHashTable<TVALUE>::GetNext (std::string* pkKey) const
00182 {
00183 if (m_iQuantity > 0)
00184 {
00185 m_pkItem = m_pkItem->m_pkNext;
00186 if (m_pkItem)
00187 {
00188 *pkKey = m_pkItem->m_kKey;
00189 return &m_pkItem->m_tValue;
00190 }
00191
00192 for (m_iIndex++; m_iIndex < m_iTableSize; m_iIndex++)
00193 {
00194 if (m_apkTable[m_iIndex])
00195 {
00196 m_pkItem = m_apkTable[m_iIndex];
00197 *pkKey = m_pkItem->m_kKey;
00198 return &m_pkItem->m_tValue;
00199 }
00200 }
00201 }
00202
00203 return 0;
00204 }
00205
00206 template <class TVALUE>
00207 int TStringHashTable<TVALUE>::HashFunction (const std::string& rkKey) const
00208 {
00209 int iHiKey = 0, iLoKey = 0;
00210 for (int i = 0; i < (int)rkKey.length(); i++)
00211 {
00212 if (i & 1)
00213 {
00214 iHiKey += (int)rkKey[i];
00215 }
00216 else
00217 {
00218 iLoKey += (int)rkKey[i];
00219 }
00220 }
00221 return abs(iLoKey * iHiKey) % m_iTableSize;
00222 }
00223
00224 }