1 /*********************************StringHash.h*********************************/ 2
3 #pragma once 4
5 #define MAXTABLELEN 1024
// 默认哈希索引表大小
6 //////////////////////////////////////////////////////////////////////////
7 // 哈希索引表定义
8 typedef struct _HASHTABLE 9
{ 10 long nHashA;
11 long nHashB;
12 bool bExists;
13 }HASHTABLE, *PHASHTABLE ; 14
15 class StringHash 16
{ 17
public: 18 StringHash(const
long nTableLength = MAXTABLELEN); 19 ~StringHash(void);
20 private:
21 unsigned
long cryptTable[0x500];
22 unsigned
long m_tablelength; // 哈希索引表长度
23 HASHTABLE *m_HashIndexTable;
24 private: 25 void InitCryptTable();
// 对哈希索引表预处理
26 unsigned long HashString(const
string& lpszString, unsigned
long dwHashType); // 求取哈希值
27 public: 28 bool Hash(string
url); 29 unsigned
long Hashed(string url);
// 检测url是否被hash过 30
}; 31
32 33 34
/*********************************StringHash.cpp*********************************/ 35
36 #include "StdAfx.h" 37 #include
"StringHash.h" 38
39 StringHash::StringHash(const
long nTableLength
/*= MAXTABLELEN*/) 40
{ 41 InitCryptTable();
42 m_tablelength = nTableLength;
43 //初始化hash表 44 m_HashIndexTable =
new HASHTABLE[nTableLength];
45 for (
int i = 0; i < nTableLength; i++ )
46 {
47 m_HashIndexTable[i].nHashA = -1;
48 m_HashIndexTable[i].nHashB = -1;
49 m_HashIndexTable[i].bExists =
false; 50 }
51 } 52
53 StringHash::~StringHash(void) 54
{ 55 //清理内存 56 if ( NULL !=
m_HashIndexTable ) 57 {
58 delete []m_HashIndexTable;
59 m_HashIndexTable = NULL;
60 m_tablelength =
0; 61 }
62 } 63
64 /************************************************************************/ 65
/*函数名:InitCryptTable 66
/*功 能:对哈希索引表预处理 67
/*返回值:无 68
/************************************************************************/ 69
void StringHash::InitCryptTable()
70 {
71 unsigned long seed =
0x00100001, index1 =
0, index2 = 0, i; 72
73 for( index1 =
0; index1 < 0x100; index1++ )
74 {
75 for( index2 = index1, i =
0; i < 5; i++, index2 +=
0x100 ) 76 {
77 unsigned
long temp1, temp2; 78 seed = (seed *
125 + 3) %
0x2AAAAB; 79 temp1 = (seed &
0xFFFF) << 0x10;
80 seed = (seed *
125 + 3) %
0x2AAAAB; 81 temp2 = (seed &
0xFFFF); 82 cryptTable[index2] = ( temp1 | temp2 );
83 }
84 } 85
} 86
87 /************************************************************************/ 88
/*函数名:HashString 89
/*功 能:求取哈希值 90
/*返回值:返回hash值 91
/************************************************************************/ 92 unsigned
long StringHash::HashString(const
string& lpszString, unsigned
long dwHashType) 93
{ 94 unsigned
char *key = (unsigned
char *)(const_cast<char*>(lpszString.c_str()));
95 unsigned
long seed1 = 0x7FED7FED, seed2 =
0xEEEEEEEE; 96 int ch; 97
98 while(*key !=
0) 99 {
100 ch = toupper(*key++);101
102 seed1 = cryptTable[(dwHashType <<
8) + ch] ^ (seed1 + seed2); 103 seed2 = ch + seed1 + seed2 + (seed2 <<
5) + 3;
104 }
105 return seed1;
106 }107
108 /************************************************************************/109
/*函数名:Hashed110
/*功 能:检测一个字符串是否被hash过111
/*返回值:如果存在,返回位置;否则,返回-1112
/************************************************************************/113 unsigned
long StringHash::Hashed(string lpszString)114
115 { 116 const unsigned
long HASH_OFFSET =
0, HASH_A = 1, HASH_B =
2; 117
//不同的字符串三次hash还会碰撞的几率无限接近于不可能118 unsigned
long nHash = HashString(lpszString, HASH_OFFSET);
119 unsigned
long nHashA = HashString(lpszString, HASH_A);
120 unsigned long nHashB = HashString(lpszString, HASH_B);
121 unsigned
long nHashStart = nHash % m_tablelength,
122 nHashPos = nHashStart;123
124 while ( m_HashIndexTable[nHashPos].bExists)
125 {
126 if (m_HashIndexTable[nHashPos].nHashA == nHashA && m_HashIndexTable[nHashPos].nHashB == nHashB)127 return
nHashPos; 128 else
129 nHashPos = (nHashPos +
1) % m_tablelength;130
131 if (nHashPos == nHashStart)
132 break;
133 }134
135 return -1;
//没有找到 136
}137
138 /************************************************************************/139
/*函数名:Hash140
/*功 能:hash一个字符串 141
/*返回值:成功,返回true;失败,返回false142
/************************************************************************/143
bool StringHash::Hash(string lpszString)144
{ 145 const unsigned
long HASH_OFFSET =
0, HASH_A = 1, HASH_B =
2; 146 unsigned
long nHash = HashString(lpszString, HASH_OFFSET);
147 unsigned
long nHashA = HashString(lpszString, HASH_A);
148 unsigned long nHashB = HashString(lpszString, HASH_B);
149 unsigned
long nHashStart = nHash % m_tablelength,
150 nHashPos = nHashStart;151
152 while ( m_HashIndexTable[nHashPos].bExists)
153 {
154 nHashPos = (nHashPos +
1) % m_tablelength; 155 if (nHashPos == nHashStart)
//一个轮回 156 {
157 //hash表中没有空余的位置了,无法完成hash158 return
false; 159 }
160 }
161 m_HashIndexTable[nHashPos].bExists =
true; 162 m_HashIndexTable[nHashPos].nHashA = nHashA;
163 m_HashIndexTable[nHashPos].nHashB = nHashB;164
165 return
true; 166 }
hash算法
最新推荐文章于 2025-07-23 17:08:17 发布