----------2019.09.10更新----------
今天突然想到了一个特别贴近生活的例子:查字典
假设我们需要查询的字为「进」,使用部首查字法。先找三划的部首,找到「辶」,在找到四划的「井」。便完成了「进」字的查找,其中执行了两次哈希运算。
如果采用遍历法的话就是从第一页开始,一页一页向后一直找,直到找到「进」字为止。
关于部首查字法可以参考百度百科
https://jingyan.baidu.com/article/46650658fc6f97f549e5f8a9.html
----------2019.09.10更新----------
由于大学不是计算机专业,从听说到Hash这个概念的时候就没弄明白到底什么是Hash函数。
这几天在学习的过程中简单接触到了Hash算法的实际案例,在这里跟广大半路出家的程序员朋友们一起分享一下。
(如果有哪里我的观点是错误的,还请大家不吝赐教)
首先题目的要求是:找出字符串中第一个出现多次的字符,例如“acbdadd”,得出结果为“c”
思路是这样的:
1.英文字母对应的ASCII码为2^8=256个,所以用一个数组内含256个0来记录输入字符串中每个字符出现的次数;
2.遍历输入字符串,通过每个元素的ASCII码找到记录该元素出现次数的位置(如“A”对应的ASCII为65,数组中的第64个元素用来记录“A”出现的次数),由于数组内使用Int型来记录出现的次数,故Array[ASCIIcode] += 1;
3.再次遍历输入的字符串,从数组中取出对应的出现次数信息,当Array[ASCIIcode] == 1时便找到目标元素。
以下是对应的代码
- (IBAction)calButtonAction:(UIButton *)sender {
//Part.1 - ASCII使用8个0/1组成,能够表示出2^8=256种可能,所以创建一个有256个元素的数组
NSMutableArray *countArray = [NSMutableArray arrayWithCapacity:256];
for (NSInteger i = 0; i < 256; i++) {
NSNumber *zero = [NSNumber numberWithInt:0];
[countArray addObject:zero];
}
//Part.2
NSString *proString = self.inputer.text;
for (NSInteger i = 0; i < proString.length; i++) {
NSInteger asc = [proString characterAtIndex:i]; //直接输出ASCII值
NSInteger count = [countArray[asc-1] integerValue];
count = count + 1;
//在查找和替换的过程中,通过计算得到储存位置,而为一个个遍历,这样的一个过程是哈希函数
[countArray replaceObjectAtIndex:(asc-1) withObject:@(count)];
}
//Part.3 - 应该根据输入的顺序进行遍历
NSString *result;
for (int i = 0; i < proString.length; i++) {
NSInteger count = [countArray[[proString characterAtIndex:i]-1] integerValue];
if (count == 1) {
//找到第一个只出现一次的元素,可以结束循环
result = [proString substringWithRange:NSMakeRange(i, 1)];
break; //不再继续循环
}
}
self.requltLabel.text = [NSString stringWithFormat:@"The result is : %@",result];
}
----------分割线----------
那么这个过程中哪里涉及到Hash了呢?
计算元素的ASCII码,再通过ASCII为索引到数组中查找数据,就是一次哈希查找了。
GitHub代码
大家觉得不错的话拜托给我个🌟
有哪里觉得我说的不清楚请留言
网友评论