OC与c混编实现Java的String的hashcode()函数

首先,我不愿意大家需要用到这篇文章里的代码,因为基本上你就是被坑了。
起因:我被Java后台人员坑了一把,他们要对请求的参数增加一个额外的字段,字段的用途是来校验其余的参数是否再传递过程中被篡改或因为网络原因出现错误。校验就校验吧,居然选了Java的String的hashcode()函数作为校验手段,安卓自然完全没有问题。但是iOS上。。。。。我又继续询问他能否改成比较通用的校验手段,比如md5等,反馈是安卓已经上线了。然后无奈职能按照Java的实现做了一把。

先贴出代码吧

-(int)DF_hashCode {
    int hash = 0;
    for (int i = 0; i<[self length]; i++) {
        NSString *s = [self substringWithRange:NSMakeRange(i, 1)];
        char *unicode = (char *)[s cStringUsingEncoding:NSUnicodeStringEncoding];
        int charactorUnicode = 0;
        size_t length = strlen(unicode);
        for (int n = 0; n < length; n ++) {
            charactorUnicode += (int)((unicode[n] & 0xff) << (n * sizeof(char) * 8));
        }
        hash = hash * 31 + charactorUnicode;
    }
    
    return hash;
}

我写个了个分类处理这个hashcode
首先获取每个字符,获取到字符后转成unicode,这里调试了很久,因为安卓的同事认为是utf8编码,因为这跟网上许多加密结果显示的是一致,经过仔细比对,发现是unicode编码。如果是中文字的话,那么就是2个字节,因为编码后是以char *输出,所有对两个字节进行合并成一个short类型。如果是英文或标点,那么就是1个字节,我为乐整齐,就统一用for循环。其实获取到了length不是1个就是2。
尽管代码很短,但是已经很长时间没有直接使用c了,连着调试和寻找编码的格式,还是花了不少时间。希望你们别走弯路,不到万不得已不要这样校验。

posted @ 2016-03-29 17:20  钱鸿强  阅读(1108)  评论(0编辑  收藏  举报