一. strtok函数的使用
继续上次的学习,今天我们来认识一个新的函数strtok,它的原型是char* strtok(char* str,const char* sep),sep参数指向了一个字符串,定义了用作分隔符的字符合集,第一个参数指定⼀个字符串,它包含了0个或者多个由sep字符串中一个或者多个分隔符分割的标记。strtok函数找到str中的下一个标记,并将其用 \0 结尾,返回一个指向这个标记的指针。(注:strtok函数会改变被操作的字符串,所以被strtok函数切分的字符串⼀般都是临时拷贝的内容并且可修改。)
让我们来实践一下:下面展示一些 内联代码片
。
int main()
{
char arr[] = { "[email protected]" };
char* p = "@.";
char* ret = strtok(arr, p);
printf("%s\n", ret);
char* ret1 = strtok(NULL, p);
printf("%s\n", ret1);
char* ret2 = strtok(NULL, p);
printf("%s\n", ret2);
return 0;
}
从上面的代码可以看出,我们定义了一个指针p指向了分隔符@和. 最终我们实现了数组arr的分割,而我们也注意到strtok函数的第一个参数为数组arr,但是后面的参数是NULL,因为函数strtok将在第一个字符串被保存的位置查找下一个标记,所以后面的参数设置成NULL,原因是为了让函数记住上一次分割的位置,而不是从头开始。
二. strstr函数的使用和模拟实现
strstr函数的原型是char * strstr ( const char * str1, const char * str2); 它的作用是在str1这个字符串中找到str2这个字符串。它具体是怎么使用的呢?让我们来实践一下:
下面展示一些 内联代码片
。
#include <stdio.h>
#include <string.h>
int main ()
{
char str[] ="This is a simple string";
char * pch;
pch = strstr (str,"simple");
strncpy (pch,"sample",6);
printf("%s\n", str);
return 0;
}
首先定义一个char*类型的指针pch,使用strstr函数在定义好的str字符串中找到simple这个字符串再返回给pch,然后我们再使用strncpy函数打印出来pch,结果如上图所示。那么我们自己如何来模拟实习呢?
看到上面的图片,我们究竟要怎样设置我们的strstr函数呢?为什么要设置这么多的指针呢?我们直接来看第二种情况,str1和str2分别指向数组的首元素地址,但是正因为需要多次匹配,我们才需要一个一直指向首元素的指针地址,所以我们创建了s1和s2两个指针,将s1和s2移动来判断两个数组中的元素是否相等,至于cur指针,它的作用就是记录第一个相等的元素,让我们用代码说明:首先我们要保证各个指针不是空指针,根据上面的图片,先让cur指针等于str1指针,使用while循环:下面展示一些 内联代码片
。
while(*cur!='\0')
{
s1=cur;
s2=str2;
while(*s1!='\0' && *s2!='\0'&& *s1==*s2)
{
s1++;
s2++;
}
if(*s2=='\0')
return cur;
cur++;
}
上面的代码虽然不完整,但是也有一定的实用性了,我们先让s1和s2分别位于数组的首元素地址,然后进入一个循环,如果s1等于s2说明此时有可能找到一样的字符,那我们就让s1++和s2++,一旦s1和s2不相等,我们就跳出循环,直接让我们的cur++,找到下一个字符再重新开始,比如上图中,当arr数组中的a和p数组中的字符b不相等时,我们直接让cur++,然后再将cur指针重新赋给s1,此时的s1就指向字符b,而s2也指向字符b,那么我们就进入了第二个while循环,条件是s1和s2相等,如果不相等,就跳出第二个循环,说明不匹配,再让cur++,指向下一个字符,再重新开始匹配,当我们s1和s2再一次++,s1指向arr数组中的第二个b,而p中的s2指向了字符c,此时不满足条件,跳出循环,然后cur++,再重新开始,那么此时如果再将cur赋给s1的话,便是指向arr数组中的第二个b,如果从此刻开始,我们就算是匹配成功了,大家下去可将这个过程自己演示一遍.
下面展示一些 内联代码片
。
char* my_strstr(const char* str1, const char* str2)
{
assert(str1 && str2);
const char* s1 = NULL;
const char* s2 = NULL;
const char* cur = str1;
while(*cur!='\0')
{
s1=cur;
s2=str2;
while(*s1!='\0' && *s2!='\0'&& *s1==*s2)
{
s1++;
s2++;
}
if(*s2=='\0')
return cur;
cur++;
}
return NULL;
}
三. strerror函数的使用
我们来学习下一个函数strerror函数,它的原型是char* strerror ( int errnum ); strerror 函数可以把参数部分错误码对应的错误信息的字符串地址返回来。
在不同的系统和C语言标准库的实现中都规定了一些错误码,一般是放在 errno.h 这个头文件中说明的,C语言程序启动的时候就会使用一个全局的变量errno来记录程序的当前错误码,只不过程序启动的时候errno是0,表示没有错误,当我们在使用标准库中的函数的时候发生了某种错误,就会将对应的错误码,存放在errno中,而一个错误码的数字是整数很难理解是什么意思,所以每⼀个错误码都是有对应的错误信息的。strerror函数就可以将错误对应的错误信息字符串的地址返回。
我们来举一个例子:下面展示一些 内联代码片
。
#include <errno.h>
#include <string.h>
#include <stdio.h>
//我们打印⼀下0~10这些错误码对应的信息
int main()
{
int i = 0;
for (i = 0; i <= 10; i++)
{
printf("%s\n", strerror(i));
}
return 0;
}
在以后的使用中我们可能会用到上述函数,当我们理解这些函数的内部结构以及作用我们使用起来才会更加得心应手.