我们知道CRT函数strchr()所做的事情就是在字符串中查找特定的字符,那么它是如何实现的呢?请看下面的代码:
char* SimpleFind(char* str, int n)
{
while(*str != '\0' && *str != n)
++str;
return *str == n ? str : (char*)0;
}
SimpleFind()函数同样完成了strchr()所做的事情,实际上strchr()基本上就是采用这种方式实现的。需要回答两个问题:
(1) 为什么返回值要设置成char*而非int表示字符的位置?
这样做方便SimpleFind()的嵌套调用,如SimpleFind(SimpleFind(s,'a') + 1, 'a'),首先查找字符串s中第一个字符'a',然后查找第2个字符'a'。由于返回值类型就是char*,本身就可以当作SimpleFind()的参数。
(2) 怎么判断字符串的末尾?
如代码所示,C字符串的最后一个字符是'\0',以它作为字符串末尾的标志。
这样便引出新的问题,如果被查找的字符串不是以'\0'结尾呢?比如想要在str的前10个字符中查找。如果直接调用上面的SimpleFind(),判断字符串结尾的方法就不对。针对这个问题,我们定义SimplFind()的重载函数,如下所示:
char* SimpleFind(char* start, char* end, int n)
{
while(start != end && *start != n)
++start;
return *start == n ? start : (char*)0;
}
SimpleFind()的重载版本接受的是一个区间[start, end),判断字符串结尾的方式也改成了if(start == end),这样一来SimpleFind()就可以应付更多情况。
下面编写一个小的程序测试SimpleFind()的功能:
/* SimpleFind.cpp
* created: ume
* date: 2011-12-18
* remarks:
*
*/
#include<iostream>
using namespace std;
// function: SimpleFind
char* SimpleFind(char* str, int n)
{
while(*str != '\0' && *str != n)
++str;
return *str == n ? str : (char*)0;
}
char* SimpleFind(char* start, char* end, int n)
{
while(start != end && *start != n)
++start;
return *start == n ? start : (char*)0;
}
// main function
int main()
{
char sentence[256];
cin>>sentence;
char* first2 = SimpleFind(sentence,'2');
if(!first2)
{
cout<<"一个2也没有\n";
goto end;
}
char* second2 = SimpleFind(first2+1,'2');
if(!second2)
{
cout<<"只找到一个2\n";
goto end;
}
if(SimpleFind(first2,second2,'B'))
{
cout<<"在2个2之间找到一个字母B\n";
goto end;
}
if(SimpleFind(first2,second2,'b'))
{
cout<<"在2个2之间找到一个字母b\n";
goto end;
}
cout<<"在2个2之间没有找到想要的字母\n";
end:
system("pause");
return 0;
}
然后输入一个测试用例,结果是这样的:
zzzzzzzzzzzzzz2zzzzzzzb2
在2个2之间找到一个字母b
请按任意键继续. . .
这个例子非常简单,只是一个简单的字符串比对。之后我们将考虑将它模板化,并引入迭代器使得它更具有通用性,请关注后续文章。