字符串库函数总和讲解及各自实现(含strlen、strcpy、strcat、strcmp、strstr、strtok、strerror)


1、字符串库函数讲解及各自实现
1.1 strlen
1.1.1 strlen的使用及注意事项
1.1.2 strlen的实现
1.2 strcpy
1.2.1 strcpy的使用和注意事项
1.2.2 strcpy的实现
1.3 strcat
1.3.1 strcat的使用及注意事项
1.3.2 strcat的实现
1.4 strcmp
1.4.1 strcmp的使用及注意事项
1.4.2 strcmp的实现
1.4 strstr
1.4.1 strstr的使用及注意事项
1.4.2 strstr的实现
1.5 strtok
1.5.1 strtok的使用及注意事项
1.6 strerror
1.6.1 strerror的使用及注意事项
2、完结撒花

1、字符串库函数讲解及各自实现
在我们学习C语言中对与字符串的使用和操作方式有很多种,为了方便我们操作字符串,开发者们写出了许多处理字符串的库函数供我们使用,提前说一下,所有的字符串库函数使用时都必须包含头文件string.h,下面就让我们来一起学习。
1.1 strlen
1.1.1 strlen的使用及注意事项
大家学习C语言对于strlen这个最基本的字符串库函数应该也都不陌生,strlen是用来计算字符串长度所使用的。使用时记得带上头文件string.h。对于strlen函数在计算字符串长度时是遇到字符‘\0’就停止计算,得出该字符串的长度,所计算的长度不包含‘\0’。我们可以简单上手敲一个
在这里插入图片描述在使用strlen时还需要注意一点,我们可以打开MSDN搜索一下该函数,如下图
在这里插入图片描述我问可以看到其对strlen的介绍,需要注意的是strlen这个库函数的返回值的类型为size_t,所以在使用该库函数要避免对使用该库函数所得到的返回值进行运算,如:
在这里插入图片描述很明显arr1长度小于arr2,结果应打印<才对,但却出现了bug,因为strlen的返回值为无符号整数类型,两个无符号整数类型相减得到的也应为无符号整数类型,所以无符号类型4-7将会得到一个非常大的整数,所以最后打印为>。
1.1.2 strlen的实现
我们参照MSDN对strlen的介绍,对strlen进行一个简单实现,代码如下:

size_t my_strlen(const char* str)
{
	assert(str);
	size_t count = 0;
	while (*str != '\0')
	{
		str++;
		count++;
	}
	return count;
}

int main()
{
	char arr[] = "abcdef";
	size_t len = my_strlen(arr);
	printf("%u", len);
	return 0;
}

该代码为计数器方法实现strlen,其实还有多种实现方法比如用递归实现,或是指针相减,感兴趣的可以自己尝试实现一下,有大牛会的话可以发在评论区供大家参考学习,谢谢啦。
1.2 strcpy
1.2.1 strcpy的使用和注意事项
strcpy为字符串拷贝函数,将一个字符串的内容拷贝为另一个字符串的内容,同样在使用的时候要包含头文件string.h,在拷贝时会连同字符串中的‘\0’一同拷贝到另一个字符串当中去,如图:
在这里插入图片描述可以看到在拷贝之后的arr1数组中在字符‘X’前面含有‘\0’。在使用strcpy对字符串进行拷贝时,还需保证arr1的数组空间够用来存放arr2,在数组arr2中要有字符‘\0’,不然系统会出现错误崩溃。
1.2.2 strcpy的实现
同样我们参考MSDN中的介绍标准,对strcpy进行实现
在这里插入图片描述可以看出库函数strcpy的返回类型为char*,并且形参为两个char*类型的指针。这不难想到所传的实参为两个字符串的数组名。代码如下:

char* my_strcpy(char* dest, const char* str)
{
	assert(dest && str);
	char* ret = dest;
	while (*dest++ = *str++)
		;
	return dest;
}

int main()
{
	char arr1[10] = "XXXXXXXXX";
	char arr2[] = "abcdefg";
	my_strcpy(arr1, arr2);
	printf("%s", arr1);
	return 0;
}

1.3 strcat
1.3.1 strcat的使用及注意事项
strcat是字符串追加函数,顾名思义,就是可以将两个字符串拼接起来,在使用时要注意,要拼接的字符串必须含有字符‘\0’,以保证是自己所输入的那个完整的字符串,再拼接到另一个字符串上去,不可以是下图所示情况:
在这里插入图片描述这个代码中字符串arr2便没有字符’\0’,系统编译便会崩溃。
其次是目标空间需足够大,以容得下拼接好的字符串,如下图:
在这里插入图片描述在使用strcat函数时,还有一种情况就是一个字符串本身是否可以拼接自己,既strcat(arr1,arr1);,答案为不可以,具体原因我们来对strcat进行实现之后便可以知道。
1.3.2 strcat的实现
我们依然参考MSDN上面对strcat进行实现
在这里插入图片描述strcat的返回类型也为char*类型,其形参与strcpy也一样,所以我们进行实现的代码如下:

char* my_strcat(char* dest, const char* str)
{
	assert(dest && str);
	char* ret = dest;
	while (*dest)
	{
		dest++;
	}
	while (*dest++ = *str++)
		;
	return ret;
}

int main()
{
	char arr1[15] = "HOLLE";
	char arr2[] = " WORLD";
	my_strcat(arr1, arr2);
	printf("%s", arr1);
	return 0;
}

因为在实现strcat函数的时候对arr1所传的形参指针的位置发生了改变,所以想在对其本身进行拼接行不通的。
1.4 strcmp
1.4.1 strcmp的使用及注意事项
strcmp是比较字符串大小的库函数,对所比较的两个字符串中每个字符的ASCLII码值进行逐个比较,从第一个字符比较开始,如果相等就比较下一个字符,如果arr1大于arr2则返回一个大于零的数,小于则返回一个小于零的数,使用实列:
在这里插入图片描述1.4.2 strcmp的实现
接下来我们还根据MSDN上面对strcmp函数进行实现
在这里插入图片描述对于返回值是int类型,如果arr1>arr2则我们就定义返回1,arr1=arr2返回0,arr1<arr2返回-1。
实现代码如下:

int my_strcmp(const char* str1, const char* str2)
{
	assert(str1 && str2);
	while (*str1 == *str2)
	{
		if (*str1 == '\0')
		{
			return 0;
		}
		str1++;
		str2++;
	}
	if (*str1 > *str2)
	{
		return 1;
	}
	else
	{
		return -1;
	}
}

int main()
{
	char arr1[] = "abcdefg";
	char arr2[] = "abcp";
	int ret = my_strcmp(arr1, arr2);
	if (ret == 0)
	{
		printf("==");
	}
	else if (ret < 0)
	{
		printf("<");
	}
	else if (ret > 0)
	{
		printf(">");
	}
	return 0;
}

1.4 strstr
1.4.1 strstr的使用及注意事项
strstr是字符串查找函数,顾名思义,在第一个字符串中查找是否存在另一个字符串,若是存在另一个字符串,则会返回第一个字符串中与另一个字符串的第一个字符相同的字符的地址,若不存在另一个字符串则会返回空指针NULL,使用实列:
在这里插入图片描述大家也可以自己上手实践一下,印象会更加深刻。
看到实列中,arr1字符串中存在arr2字符串,所以返回了arr1字符串中字符‘d’的地址存到了ret中,打印字符串从ret即字符‘b’的地址开始便得到了“defghi”。
1.4.2 strstr的实现
对于strstr的实现与之前的字符串函数相比起来就比较复杂了,在这里插入图片描述可以看到strstr函数的返回值为char*类型,即若是存在则会返回一个字符的地址,若是不存在则返回NULL,我们先看实现的代码在对其进行讲解

char* my_strstr(const char* str1, const char* str2)
{
	assert(str1 && str2);
	const char* s1 = str1;
	const char* s2 = str2;
	const char* p = str1;
	while (*p)
	{
		s1 = p;
		s2 = str2;
		while (*s1!='\0' && *s2!='\0' && *s1 == *s2)
		{
			s1++;
			s2++;
		}
		if (*s2 == '\0')
		{
			return p;
		}
		p++;
	}
}

int main()
{
	char arr1[] = "abcdefghi";
	char arr2[] = "def";
	char* ret = my_strstr(arr1, arr2);
	if (ret == NULL)
	{
		printf("没有该字符串\n");
	}
	else
	{
		printf("%s", ret);
	}
	return 0;
}

对于strstr的实现我们首先需要明白查找的原理,在arr1中查找是否有arr2字符串,在查找时上述状况arr1是“abcdefghi”,arr2是“def”这是最简单的一种状况,一边查询即可搞定,但假设如果arr1是“abbbcdef”而arr2是“bbcd”,这时候进行一边的查找显然是解决不了的,因为在查找到第一个字符’b’时,两个字符串一致,继续向后查找,第二个字符’b‘也一致,查找到第三个字符时却产生了差异,这时肯定不能继续在查下去,我们需要从arr1的第二个字符’b‘再重新开始与arr2的字符一一对应的找,所以我们就需要对arr1和arr2中第一个相同的字符进行标记,如果向后查找出现了不同,则回头从所标记的位置加1再开始进行查找。
1.5 strtok
1.5.1 strtok的使用及注意事项
strtok是字符串切割函数,用来划分字符串,实列如下:
在这里插入图片描述如图,在使用strtok时,我们需要把分隔符也定义在一个字符串中,在要进行分割的字符串中遇到分隔符就会返回前面字符串首字符的地址,这时定义一个相同类型的变量接收打印即可,当字符串分割完后会返回空指针NULL,结束分割,所以我们可以使用for循环进行打印,而且我们在对字符串进行分割后会改变原本的字符串,所以我们在分割时一般分割的是原字符串的一份临时拷贝,以避免接下来可能会带来不便。
1.6 strerror
1.6.1 strerror的使用及注意事项
strerror库函数,其实与字符串的关系不大,这里我们也顺便讲解一下。
strerror的功能是返回错误码对应的错误信息。在C语言中1,2,3,4…等,都可以表示为错误码,每个错误码都有其对应的错误信息。比如:
在这里插入图片描述这些错误码和对应的错误信息并不需要全部记住,因为库函数在执行失败后会自动生成所对应的错误码,我们只需要将错误码转化为错误信息即可,下面我们以打开电脑中的一个文件为例给大家演示:
在这里插入图片描述在C语言中调用库函数执行产生错误的话错误码都会放在errno当中去,errno是一个全局的错误码存放变量,在我的电脑中并没有“text.txt”这个文件,所以执行会产生错误,产生的错误码就会放在errno里面,我们使用strerror便可将错误码转化成对应的错误信息。
2、完结撒花
这次的知识分享给大家讲解了常用的字符串库函数,如果对你有帮助的话不妨点个赞,如果还有什么不会的,或者是没搞懂的可以私信或者评论留言,之后我也会分享更多的知识,谢谢支持。

  • 28
    点赞
  • 25
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值