题目:字符串中第一个只出现一次的字符。
在字符串中找出第一个只出现一次的字,如输入“abaccdeff”,则输出’b’。
很多人读完这道题,会觉得这道题看起来并不难,只需要 从头开始扫描这个字符串的每一个字符,当访问到某个字符时,拿这个字符和后面的每个字符相比较,如果后面没有发现重复的字符,则该字符就是只出现一次的字符。
这样的做法的时间复杂度是O(N²),是想:如果题目要求时间复杂度为O(N),又或者这里不是求第一次只出现一次的字符,而是2次,3次…k次呢?
其实我们可以考虑实现一个简单的哈希表,已知字符是一个长度为8的数据类型,因此总共有256中可能。于是我们创建一个长度为256的数组,每个字母根据其ASCII码值作为数组的下标对应数组的一个数字,而数组存储的是每个字符出现的次数。
第一次扫描时,在哈希表中更新每个字符出现的次数,时间复杂度为O(N),第二次查找时,只需要根据ASCII码值找到数组中的位置即可读出出现的次数,所以时间复杂度仍为O(N),同时,我们开辟了一个包含256个字符的辅助数组,大小是1kb,这个数组的大小是常数,所以总的时间复杂度为O(N)。
下面是参考代码:
char FindFirstKTimesChar(char* pStr, int k)//查找字符串中第一次出现k次的字符
{
if (*pStr == NULL || k <= 0)
return '\0';
int hashTable[256] = {0};
char* p = pStr;
while (*p != '\0')
{
hashTable[*p]++;
p++;
}
p = pStr;
while (*p != '\0')
{
if (hashTable[*p] == k)
return *p;
p++;
}
return '\0';
}