C编译器是否识别2的幂?
我正在构建一个自定义哈希,我根据公式对字符串中的所有字母求和:
string[0] * 65536 + string[1] * 32768 + string[2] * 16384 + ... 而且我遇到了一个问题,我是否应该将这些数字定义为int数组中的常量,如下所示: const int MULTIPLICATION[] = { 65536,32768,16384,8192,4096,2048,1024,512,256,128,64,32,16,8,4,2,1 } 或者,也许我应该在计算哈希本身时生成这些数字(虽然由于它们尚未生成而可能会失去一些速度)? MOV EBX,8 MUL EBX 它会的 SHL EAX,3 编译器是否理解如果我乘以2的幂来移位而不是通常的乘法? 另一个问题,我很确定当你用c写的时候它会移位 谢谢,我已经找到了如何在调试器中查看dissasembly.是的,如果您使用它,编译器确实理解移位 number *= 65536 但是,如果你这样做,它会进行正常的乘法运算 number1 = 65536 number *= number1; 解决方法
试试吧!
你用的是什么编译器?您可以告诉大多数编译器在编译后保留中间文件,或者只编译(而不是汇编),这样您就可以实际查看它生成的汇编代码. 你可以在这other question of mine上看到这就是我所做的. 例如,在gcc中,-S标志表示“仅编译”.并且-masm = intel生成更可读的程序集,IMO. 编辑 总而言之,我认为以下是您正在寻找的算法(未经测试): // Rotate right by n bits #define ROR(a,n) ((a >> n) | (a << (sizeof(a)*8-n))) int custom_hash(const char* str,int len) { int hash = 0; int mult = 0x10000; // 65536,but more obvious for (int i=0; i<len; i++) { hash += str[i] * mult; mult = ROR(mult,1); } return mult; } 首先,你没有指定当你有超过16个字符时会发生什么(乘数是多少?)所以在这个实现中,我使用了一个按位旋转. x86有bitwise rotate instructions(ror和rol分别为左右旋转).但是,C没有提供表达旋转操作的方法.所以我定义了为你做旋转的ROR宏. (了解它的工作原理留给读者练习!) 在我的循环中,我像你一样在0x10000(65536)开始乘数.循环的每次迭代,我将乘数右旋一位.这基本上将它除以2,直到达到1,之后变为0x80000000. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |