Encapsulation and testing of warcraft Hash Algorithms

Source: Internet
Author: User

Recently, due to the need, we have studied the related algorithms of the Warcraft file packaging manager, focusing on the generation and search of its file index tables: Using hash tables, in terms of conflict processing, uses linear detection and then hashes. Three hashes are performed during addition and search. The first hash value is used for search, and the last two hash values are used for verification. This greatly reduces the chance of conflict.

It is simply encapsulated here. During expansion, you only need to expand the struct. For more details, refer to the Code: [reprinted, Please retain the copyright, thank you]

 

I. Class declaration header file

 

//////////////////////////////////////// /// // <Br/> // Name: hashalgo. h <br/> // purpose: uses the World of Warcraft hash algorithm to fill and search the index table. <Br/> // Author: Chen xiangli <br/> // modified by: <br/> // created: 07/30/09 <br/> // RCS-ID: $ ID: treetest. h 43021 16: 36: 51z VZ $ <br/> // copyright: (c) Copyright 2009, tsong Corporation, All rights reserved. <br/> // licence: <br/> //////////////////////////////////// //////////////////////////////////////// /</P> <p> # define maxfilename 255 // Maximum File Name Length <br/> # define maxtablelen 1024 // default hash index table size </P> <p> //////////////////////////////////////// /// // <Br/> // test macro definition, close <br/> # define debugtest 1 </P> <p> ///////////////////// //////////////////////////////////////// /////// // <br/> // hash index table definition <br/> typedef struct <br/> {<br/> long nhasha; <br/> long nhashb; <br/> bool bexists; <br/> char test_filename [maxfilename]; <br/> //...... <br/>} mpqhashtable; </P> <p> ////////////// //////////////////////////////////////// //////////////// <Br/> // encapsulate the algorithm of the hash index table <br/> class chashalgo <br/>{< br/> public: </P> <p> # If debugtest <br/> long testid; // test <br/> # endif </P> <p> chashalgo (const long ntablelength = maxtablelen) // create a hash index table of the specified size, create a hash index table of the default size by using a constructor without parameters <br/>{< br/> preparecrypttable (); <br/> m_tablelength = ntablelength; </P> <p> m_hashindextable = new mpqhashtable [ntablele Ngth]; <br/> for (INT I = 0; I <ntablelength; I ++) <br/>{< br/> m_hashindextable [I]. nhasha =-1; <br/> m_hashindextable [I]. nhashb =-1; <br/> m_hashindextable [I]. bexists = false; <br/> m_hashindextable [I]. test_filename [0] = '/0'; <br/>}</P> <p> void preparecrypttable (); // pre-processing the hash index table </P> <p> unsigned long hashstring (char * lpszfilename, unsigned long dwhashtype); // obtain the hash value <br/> long getha Shtablepos (char * lpszstring); // obtain the position in the fixed-length table <br/> bool sethashtable (char * lpszstring ); // hash the string to the hash table </P> <p> unsigned long gettablelength (void); <br/> void settablelength (const unsigned long nlength ); </P> <p> ~ Chashalgo () <br/>{< br/> If (null! = M_hashindextable) <br/>{< br/> Delete [] m_hashindextable; <br/> m_hashindextable = NULL; <br/> m_tablelength = 0; <br/>}< br/> protected: </P> <p> PRIVATE: <br/> unsigned long crypttable [0x500]; <br/> unsigned long m_tablelength; // The length of the hash index table <br/> mpqhashtable * m_hashindextable; <br/> };

 

Ii. Class implementation file

 

//////////////////////////////////////// /// // <Br/> // Name: hashalgo. CPP <br/> // purpose: uses the World of Warcraft hash algorithm to populate and search the index table. <Br/> // Author: Chen xiangli <br/> // modified by: <br/> // created: 07/30/09 <br/> // RCS-ID: $ ID: treetest. h 43021 16: 36: 51z VZ $ <br/> // copyright: (c) Copyright 2009, tsong Corporation, All rights reserved. <br/> // licence: <br/> //////////////////////////////////// //////////////////////////////////////// /</P> <p> # include "windows. H "<br/> # include" hashalgo. H "</P> <p> ////////////////////////////// //////////////////////////////////////// //// <Br/> // preprocessing <br/> void chashalgo:: preparecrypttable () <br/>{< br/> unsigned long seed = 0x00100001, index1 = 0, index2 = 0, I; </P> <p> for (index1 = 0; index1 <0x100; index1 ++) <br/>{< br/> for (index2 = index1, I = 0; I <5; I ++, index2 + = 0x100) <br/>{< br/> unsigned long temp1, temp2; <br/> seed = (seed * 125 + 3) % 0x2aaaab; <br/> temp1 = (Seed & 0 xFFFF) <0x10; <br/> seed = (seed * 125 + 3) % 0x2aaaab; <br/> temp2 = (Seed & 0 xFFFF ); <br/> crypttable [index2] = (temp1 | temp2 ); <br/>}</P> <p> ////////////////// //////////////////////////////////////// /////////// <br/> // obtain the hash value <br/> unsigned long chashalgo:: hashstring (char * lpszfilename, unsigned long dwhashtype) <br/>{< br/> unsigned char * Key = (unsigned char *) lpszfil Ename; <br/> unsigned long seed1 = 0x7fed7fed, seed2 = 0 xeeeeeeee; <br/> int ch; </P> <p> while (* key! = 0) <br/>{< br/> CH = toupper (* Key ++); </P> <p> seed1 = crypttable [(dwhashtype <8) + CH] ^ (seed1 + seed2); <br/> seed2 = CH + seed1 + seed2 + (seed2 <5) + 3; <br/>}< br/> return seed1; <br/>}</P> <p> //////////////////////////// //////////////////////////////////////// ///// <br/> // obtain the position in the fixed-length table. <br/> long chashalgo:: gethashtablepos (char * lpszstring) </P> <p >{< br/> const unsigned long hash_offset = 0, hash_a = 1, hash_ B = 2; <br/> unsigned long nhash = hashstring (lpszstring, hash_offset); <br/> unsigned long nhasha = hashstring (lpszstring, hash_a ); <br/> unsigned long nhashb = hashstring (lpszstring, hash_ B); <br/> unsigned long nhashstart = nhash % m_tablelength, <br/> nhashpos = nhashstart; </P> <p> while (m_hashindextable [nhashpos]. bexists) <br/>{< br/> If (m_hashindextable [nhashpos]. nhasha = nhasha & m_hashindextable [nhashpos]. nhashb = nhashb) <br/> return nhashpos; <br/> else <br/> nhashpos = (nhashpos + 1) % m_tablelength; </P> <p> If (nhashpos = nhashstart) <br/> break; <br/>}</P> <p> return-1; // not found <br/>}< br/> /////////////////////////// //////////////////////////////////////// ////// <br/> // input a string, hash the corresponding table items to the corresponding location of the index table <br/> bool chashalgo: sethashtable (char * lpszstring) <br/>{< br/> const unsigned long hash_offset = 0, hash_a = 1, hash_ B = 2; <br/> unsigned long nhash = hashstring (lpszstring, hash_offset ); <br/> unsigned long nhasha = hashstring (lpszstring, hash_a); <br/> unsigned long nhashb = hashstring (lpszstring, hash_ B ); <br/> unsigned long nhashstart = nhash % m_tablelength, <br/> nhashpos = nhashstart; </P> <p> while (m_hashindextable [nhashpos]. bexists) <br/>{< br/> nhashpos = (nhashpos + 1) % m_tablelength; <br/> If (nhashpos = nhashstart) <br/>{</P> <p> # If debugtest <br/> testid =-1; <br/> # endif </P> <p> return false; <br/>}< br/> m_hashindextable [nhashpos]. bexists = true; <br/> m_hashindextable [nhashpos]. nhasha = nhasha; <br/> m_hashindextable [nhashpos]. nhashb = nhashb; <br/> strcpy (m_hashindextable [nhashpos]. test_filename, lpszstring); </P> <p> # If debugtest <br/> testid = nhashpos; <br/> # endif </P> <p> return true; <br/>}</P> <p> //////////////////////////// //////////////////////////////////////// ////// <br/> // obtain the length of the hash index table <br/> unsigned long chashalgo:: gettablelength (void) <br/>{< br/> return m_tablelength; <br/>}</P> <p> //////////////////////////// //////////////////////////////////////// ////// <br/> // set the hash index table length <br/> void chashalgo:: settablelength (const unsigned long nlength) <br/>{< br/> m_tablelength = nlength; <br/> return; <br/>}< br/>

 

Iii. Test the master file

 

//////////////////////////////////////// /// // <Br/> // Name: debugmain. CPP <br/> // purpose: test the class encapsulated by the hash algorithm to test the index table filling and searching functions. <Br/> // Author: Chen xiangli <br/> // modified by: <br/> // created: 07/30/09 <br/> // RCS-ID: $ ID: treetest. h 43021 16: 36: 51z VZ $ <br/> // copyright: (c) Copyright 2009, tsong Corporation, All rights reserved. <br/> // licence: <br/> //////////////////////////////////// //////////////////////////////////////// /</P> <p> //////////////////////////////// //////////////////////////////////////// // <br/> // Test Test parameter setting macro <br/> # define testnum 32 </P> <p> # include <iostream> <br/> # include <fstream> <br/> # include" hashalgo. H "</P> <p> using namespace STD; </P> <p> ///////////////////////////////// //////////////////////////////////////// /<br/> // test the main function <br/> int main (INT argc, char ** argv) <br/>{< br/> chashalgo hash_test (testnum); </P> <p> cout <"Get the length of the hash index for initialization: "<pash_test.gettablelength () <Endl; </P> <p> bool is _ Success = hash_test.sethashtable ("test"); <br/> If (is_success) <br/>{< br/> cout <"hash result 1: Success! "<Endl; <br/>}< br/> else <br/>{< br/> cout <" hash result 1: failed! "<Endl; <br/>}</P> <p> is_success = hash_test.sethashtable (" test "); <br/> If (is_success) <br/>{ <br/> cout <"hash result 2: Success! "<Endl; <br/>}< br/> else <br/>{< br/> cout <" hash result 2: failed! "<Endl; <br/>}</P> <p> long Pos = hash_test.gethashtablepos (" test "); <br/> cout <" search test string: /"test/": "<POS <Endl; <br/> Pos = hash_test.gethashtablepos (" test "); <br/> cout <"search test string:" test "hashed position:" <POS <Endl; </P> <p> ///////////////////////////////// //////////////////////////////////////// /<br/> // hash test <br/> for (INT I = 0; I <testnum; I ++) <br/>{< br/> char buff [32]; <br/> Sprintf (buff, "abcdefg % d.", I); <br/> is_success = hash_test.sethashtable (buff); <br/> is_success? Cout <buff <"hash result: successful! Location: "<pash_test.testid <Endl: cout <buff <" hash result: failed! "<Endl; <br/>}< br/> system (" pause "); <br/> //////////////////////////////////// /// // <br // query test <br/> for (INT I = 0; I <testnum; I ++) <br/>{< br/> char buff [32]; <br/> sprintf (buff, "abcdefg % d. ", I); <br/> Pos = hash_test.gethashtablepos (buff); <br/> pos! =-1? Cout <"search test string:" <buff <"hash position:" <POS <Endl: cout <buff <"conflict exists! "<Endl; <br/>}</P> <p> system (" pause "); <br/> return 0; <br/>}< br/>

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.