学习C语言(十四)——字符函数和字符串函数

目录

1.字符分类函数

2.字符转换函数

3.strlen函数的使用和模拟实现

3.1 strlen函数

3.2 strlen 函数的模拟实现

4.strcpy函数的使用和模拟实现

4.1 strcpy 函数

4.2 strcpy 函数的模拟实现

5.strcat 函数的使用和模拟实现

5.1 strcat 函数

5.2 strcat 函数的模拟实现

6.strcmp函数的使用和模拟实现

6.1 strcmp函数

6.2 strcmp 函数的模拟实现

7.strncpy 函数的使用和模拟实现

7.1 strncpy 函数

7.2 strncpy 函数的模拟实现

8.strncat 函数的使用和模拟实现

8.1 strncat 函数

8.2 strncat 函数的模拟实现

9.strncmp 函数的使用和模拟实现

9.1 strncmp 函数

9.2 strncmp 函数的模拟实现


1.字符分类函数

        C语言中有一系列的函数时专门用来做字符分类的,特就是一个字符属于什么类型的字符的。

        这些字符都需要包含一个头文件 <ctype.h>,函数如下:

函数

如果它的参数符合系列条件就返回真

iscntrl

任何控制字符

Isspace

空白字符:空格 ’ ’,换页’\f’,换行 ‘\n’ ,回车 ‘\r’,制表符 ‘\t’或者垂直制表符 ‘\v’

isdigit

十进制数字0-9

isxdigit

十六进制数字,包括所有十进制数字,小写字母a-f,大写字母A-F

islower

小写字母a~z

isupper

大写字母A~Z

isalpha

字母a~z或A~Z

isalnum

字母或者数字,a~z,A~Z,0~9

ispunct

标点符号,任何不属于数字或者字母的图形符号(可打印)

isgraph

任何图形字符

isprint

任何可打印字符,包括图形字符和空白字符

        下面来示范一下部分字符分类函数的使用方法,示例如下:

题目:写一个代码,将字符串中的小写字母转大写字母,其他字符不变。

        分析:1.需要遍历字符串,找到小写字母

                  2.将找到的小写字母转变为大写字母

        转变的办法:大写字母在ASCII码表中的值比小写字母小32,所以可以使用小写字母减去32就能得到小写字母        

2.字符转换函数

        C语言提供了两个字符转换函数:

int tolower(int c);		//将参数传递进去的小写字母转为大写字母
int tolupper(int c);	//将参数传递进去的大写字母转为小写字母

        在上面的题目中,在进行字母大小写转换时,我们使用的是ASCII码表值进行转换。这里有了转换函数,就可以使用函数进行转换了。

3.strlen函数的使用和模拟实现

3.1 strlen函数

        strlen 函数的格式如下:

size_t strlen(const char* str);
  • 字符串以 '\0' 作为结束标志,strlen 函数返回的是字符串中 '\0' 前面的字符个数(不包括 '\0')
  • 参数指向的字符串必须要以 '\0' 结束
  • strlen 函数的符号是 size_t ,是无符号的整型

        下面来对一段代码进行判断,判断输出的是 > 还是 <=。代码如下:

int main()
{
	const char* str1 = "abcdef123";
	const char* str2 = "abc";
	if (strlen(str2) - strlen(str1) > 0)
		printf(" > \n");
	else
		printf(" <= \n");
	return 0;
}

        最后输出的结果为 > ,因为 strlen 函数返回的值是无符号整型(size_t),两个无符号整型相减得到的结果还是无符号整型,所以相减之后得到的值还是大于0的整型。

3.2 strlen 函数的模拟实现

        方法一:遍历字符串,每遇到一个字符,count就+1,直到遇到 '\0' 。

#include <assert.h>
size_t  my_strlen(const char* str)
{
	size_t count = 0;
	assert(str != NULL);
	while (*str!='\0')
	{
		count++;
		str++;
	}
	return count;
}

        方法二:记住str在内存中的起始位置,然后遍历字符串,直到遇到 '\0',使用str最后的位置减去起始位置。

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

        方法三:使用递归的思想,在没有遇到遇到 '\0' 之前,就计算一个字符数量并将 str 在内存的位置+1,直到遇到 '\0',返回0。

size_t my_strlen(const char* str)
{
	if (*str == '\0')
		return 0;
	else
		return 1 + my_strlen(str+1);
}

4.strcpy函数的使用和模拟实现

4.1 strcpy 函数

        strcpy函数的格式如下:

char* strcpy(char* destination, const char* source);
  • 源字符串必须以 '\0' 结束
  • 会将源字符串中的 '\0' 拷贝到目标空间
  • 目标空间必须足够大,以确保能存放源字符串
  • 目标空间必须可以修改

        使用 strcpy 函数的示例如下:

4.2 strcpy 函数的模拟实现

        版本1:遍历字符串,将sor中的字符复制到des中,最后将 '\0' 也复制进去。

void my_strcpy(char* des, char* sor)
{
	while (*sor != '\0')	//遍历字符串,直到遇到'\0'后退出循环
	{
		*des = *sor;		//将sor中字符复制到des中
		des++;
		sor++;
	}
	*des = *sor;			//将'\0'复制到des中
}

        版本2:将复制的过程当做循环的条件,表达式的意思:先将sor中的字符复制到des中,然后再将des++和sor++。

void my_strcpy(char* des, char* sor)
{
	while (*des++ = *sor++)
	{
		;
	}
}

         版本3:对函数调用的参数进行断言,提高代码的健壮性

#include <assert.h>
void my_strcpy(char* des, char* sor)
{
	assert(des&&sor);	//des 和 sor 需要同时为真
	while (*des++ = *sor++)
	{
		;
	}
}

        版本4:des指向的空间是需要改变的,但是sor指向的空间不希望被改变

#include <assert.h>
void my_strcpy(char* des, const char* sor)
{
	assert(des&&sor);	//des 和 sor 需要同时为真
	while (*des++ = *sor++)
	{
		;
	}
}

        版本5:能返回字符串的起始位置,能够进行链式访问。

#include <assert.h>
char* my_strcpy(char* des, const char* sor)
{
	char* ret = des;
	assert(des && sor);
	while (*des++ = *sor++)
	{
		;
	}
	return ret;
}
int main()
{
	char str1[] = "Hello";
	char str2[10] = "abcd";
	printf("%s\n", my_strcpy(str2, str1));	//链式访问
	return 0;
}

5.strcat 函数的使用和模拟实现

5.1 strcat 函数

        strcat 函数的格式如下:

char * strcat ( char * destination, const char * source );
  • 源字符串必须以 '\0'  结束,否则没有办法知道从哪里结束追加
  • 目标字符串中也得有 '\0'  ,否则没有办法知道从哪里开始追加
  • 目标空间必须有足够大,能容纳下源字符串的内容
  • 目标空间必须可修改

                使用 strcat 函数的示例如下:

5.2 strcat 函数的模拟实现

        记录下des的起始位置,方便最后返回这个指针。

        先在des中遍历数组找到 '\0',然后从这个位置开始追加字符串。

6.strcmp函数的使用和模拟实现

6.1 strcmp函数

        strcmp 函数的格式如下:

int strcmp(const char* str1, const char* str2);
  • 第一个字符串大于第二个字符串,则返回大于0的数字
  • 第一个字符串等于第二个字符串,则返回0
  • 第一个字符串小于第二个字符串,则返回小于0的数字

        strcmp 函数的模拟实现:

6.2 strcmp 函数的模拟实现

        当 s1 和 s2 相等时,会进入循环,如果 s1 的值为 '\0'时,那么 s2 值和 s1 一样,返回0表示相等。如果 s1 的值不为 '\0'时,就会地址+1,继续寻找不一样的值,找到这个位置时,就可以通过ASCII码值,将 s1 和 s2 位置的值相减。得到的是正数,就是 s1 大;得到的是负数,就是 s2 大。

#include <assert.h>
int my_strcmp(const char* s1, const char* s2)
{
	assert(s1 && s2);
	while (*s1 == *s2)
	{
		if (*s1 == '\0')
			return 0;
		s1++;
		s2++;
	}
	return *s1 - *s2;
}

7.strncpy 函数的使用和模拟实现

7.1 strncpy 函数

        strncpy 函数的格式如下:

char * strncpy ( char * destination, const char * source, size_t num );

        其他的规则和 strcpy 函数的规则一致,不一致的规则如下 :

  • 拷贝 num 个字符从源字符串到目标空间
  • 如果源字符串的长度小于 num,则拷贝完源字符串之后,在目标的后边追加0,直到 num 个

        strncpy 函数的使用示例如下:

7.2 strncpy 函数的模拟实现

        和之前的 strcpy 函数的实现比较相似,只需要加上限制拷贝字符数量的条件即可。

#include <assert.h>
char* my_strncpy(char* des, const char* sor, const size_t num)
{
	char* ret = des;
	assert(des && sor);
	for (int i = 1; i<=num; i++)
			*des++ = *sor++;
	return ret;
}

8.strncat 函数的使用和模拟实现

8.1 strncat 函数

        strncat 函数的格式如下:

char * strncat ( char * destination, const char * source, size_t num );

        strncat 函数的使用示例如下:

8.2 strncat 函数的模拟实现

                strncat 函数的规则和 strcat 函数的规则一致,只需要加上限制链接字符数量的条件即可。

#include <assert.h>
char* my_strncat(char* des, const char* sor, const size_t num)
{
	assert(des &&sor);
	char* ret = des;
	while (*des != '\0')
		des++;
	for (int i = 1; i <= num; i++)
		*des++ = *sor++;
	return ret;
}}

9.strncmp 函数的使用和模拟实现

9.1 strncmp 函数

        strncmp 函数的格式如下:

int strncmp ( const char * str1, const char * str2, size_t num );

        strncmp 函数的使用示例如下: 

9.2 strncmp 函数的模拟实现

        strncmp 函数的规则和 strcmp 函数的规则类似,只需要加上限制链接字符数量的条件即可。

#include <assert.h>
int my_strncmp(const char* s1, const char* s2, const size_t num)
{
	assert(s1 && s2 && num);
	for (int i = 1; i <= num && *s1 == *s2; i++)
	{
		if (*s1 == '\0')
			return 0;
		s1++;
		s2++;
	}
	return *s1 - *s2;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值