c语言库函数及其实现

目录

一、strlen函数

1、定义

2、strlen的易错点

3、strlen的三种模拟实现方式

二、strcpy函数

1、定义

2、strcpy的模拟实现。

三、strcmp函数

 1、定义

2、strcmp的模拟实现

 四、strstr函数

1、定义

2、strstr的模拟实现

 五、strcat函数

1、定义

2、注意事项

 六、memcpy函数

1、定义

2、memcpy模拟实现

 七、memmove函数

1、定义

2、memmove函数模拟实现


一、strlen函数

1、定义

strlen函数是用来计算字符串的长度的,这个字符串必须以 '\0' 作为结束标记,计算的是 ‘\0’ 前面出现的字符个数,其返回值是size_t(无符号整数)。

它的使用:

#include<stdio.h>

int main()
{
	char arr[] = "abcdefgh";
	size_t ret = strlen(arr);
	printf("%u\n", ret);
	return 0;
}

 这段代码打印“8”.

2、strlen的易错点

1、我们要时刻记住strlen的返回值是size_t(无符号整数)。

下面让我们看一个例子:

#include<stdio.h>
#include<string.h>
int main()
{
	const char* str1 = "abcdefg";
	const char* str2 = "bbb";
	if (strlen(str2) - strlen(str1) > 0)
	{
		printf("哈哈");
	}
	else
	{
		printf("呵呵");
	}
	return 0;
}

这段代码会打印什么呢?打印“哈哈”,为什么呢?因为strlen返回值是size_t,所以无论怎么减,返回的是一个无符号数,一定大于0,因此打印“哈哈”

2、

	char arr[] = { 'a', 'b', 'c' };
	size_t sz = strlen(arr);

 这个sz的值会>=3,因为arr没有‘\0’,所以strlen会继续往后统计个数,知道遇到'\0'为止。

3、strlen的三种模拟实现方式

size_t my_strlen(const char* arr)
{
	assert(*arr);
	size_t ret = 0;
	while (*arr)
	{
		ret++;
		arr++;
	}
	return ret;
}


//方法2
//int my_strlen(const char* str)
//{
//	if (*str == '\0')
//		return 0;
//	else
//		return 1 + my_strlen(str + 1);
//}

//方法3
int my_strlen(char* s)
{
	char* p = s;
	while (*p != '\0')
		p++;
	return p - s;
}

二、strcpy函数

1、定义

strcpy称为字符串拷贝函数。

第一个参数为目标空间,第二个参数为源字符串,是将源字符串拷贝到目标空间中,源字符串必须以‘\0’结束,目标空间必须够大,足以放下源字符串。

例如:

int main()
{
	 char str1[] = "xxxxxxxxxx";
	 char str2[] = "bbb";
	 strcpy(str1, str2);
	 printf("%s", str1);
	return 0;
}

 将str2的内容拷贝到str1中,将打印

因为拷贝会将str2中的‘\0’也拷贝过去,所以打印的时候,遇到‘\0’就停止打印,所以只打印了‘bbb’

2、strcpy的模拟实现。

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

三、strcmp函数

 1、定义

strcmp函数称为字符串比较函数。

规定:

第一个字符串大于第二个字符串,则返回大于0的数字

第一个字符串等于第二个字符串,则返回0

第一个字符串小于第二个字符串,则返回小于0的数字

注意:字符串比较的不是长度而是内容

例如:

int main()
{
	 char str1[] = "abcdefgh";
	 char str2[] = "abcq";
	 int ret = strcmp(str1, str2);
	 printf("%d", ret);
	
	return 0;
}

这段代码将打印-1(小于0的数字),因为str1与str2的前三个字符相同,但第四个字符中,str1的‘d’要小于str2中的‘q’,所以第一个字符串小于第二个字符串,则返回小于0的数字。

2、strcmp的模拟实现

int my_strcmp (const char * src, const char * dst)
{
  int ret = 0 ;
 assert(src != NULL);
  assert(dest != NULL);
  while( ! (ret = *(unsigned char *)src - *(unsigned char *)dst) && *dst)
    ++src, ++dst;
​
  if ( ret < 0 )
    ret = -1 ;
  else if ( ret > 0 )
    ret = 1 ;
​
  return( ret );
}

 四、strstr函数

1、定义

strstr函数称为字符串查找函数。

 在第一个参数的字符中查找第二个字符串第一次出现的位置。如果找到了,返回第一个字符串中出现的第二个字符串的起始位置,如果没有找到返回NULL.

例如:

int main()
{
	char arr1[] = "i am good student, hehe student";
	char arr2[] = "student";
	//查找arr1中arr2第一次出现的位置
	char *ret = strstr(arr1, arr2);

	if (ret == NULL)
	{
		printf("找不到\n");
	}
	else
	{
		printf("%s\n", ret);
	}
	return 0;
}

这段代码打印:

2、strstr的模拟实现

char* my_strstr(const char* str1, const char* str2)

{

	assert(str1 && str2);

	

	

	char* s1;

	char* s2;

	char* cp = str1;

	if (*str2 == '\0')

	{

		return str1;

	}

	while (*cp)

	{

		s1 = cp;

		s2 = str2;

		while (*s1 && *s2 && *s1 == *s2)

		{

			s1++;

			s2++;

		}

		if (*s2 == '\0')

		{

			return cp;

		}

		cp++;

	}

	return NULL;

}

 五、strcat函数

1、定义

strcat称为字符串追加函数。

 即给第一个字符串(目标空间)追加上第二个字符串(源字符串)。

注意:源字符串必须以"\0'结束。
         会将源字符串中的“0'拷贝到目标空间。
        目标空间必须足够大,以确保能存放源字符串。

例如:

int main()
{
	char arr1[40] = "abc";
	char arr2[] = "defgh";
	int ret = strcat(arr1, arr2);
	printf("%s", ret);
	return 0;
}

 这段代码打印:

2、注意事项

源字符串必须以"\0'结束。

char arr[20]=”abc”;
char arr2[ ]={‘d’,’e’,’f’};
strcat(arr1,arr2);

如果这样使用strcat,程序会报错,因为不知道arr2什么时候结束(即arr2中没有\0,\0不知道何时出现)

 六、memcpy函数

1、定义

memcpy()内存拷贝函数

第一个参数为目标空间,第二个参数为源空间,第三个参数为要拷贝的内存的字节数。

例子:

注意:memcpy()函数只完成了不重叠的内存拷贝任务

例如:我们要把1、2、3、4放在3、4、5、6的位置,让数组变成1、2、1、2、3、4、7、8、9、10。使用.memcpy()函数我们发现不能完成任务

要完成这个任务,我们需要用memmove()函数。

2、memcpy模拟实现

 七、memmove函数

1、定义

. memmove()函数---同样也是内存拷贝函数,但是函数完成了重叠的内存拷贝任务和不重叠的内存拷贝任务,是.memcpy()函数的升级版

例子:

2、memmove函数模拟实现


void* my_memmove(void* dst, const void* src, size_t count)
{
    void* ret = dst;
    if (dst <= src || (char*)dst >= ((char*)src + count)) {
        while (count--) {
            *(char*)dst = *(char*)src;
            dst = (char*)dst + 1;
            src = (char*)src + 1;
        }
    }
    else
    {
        dst = (char*)dst + count - 1;
        src = (char*)src + count - 1;
        while (count--) {
            *(char*)dst = *(char*)src;
            dst = (char*)dst - 1;
            src = (char*)src - 1;
        }
    }
    return ret;
}


int main()
{
    int arr1[] = { 1,2,3,4,5,6,7,8,9,10 };
    my_memmove(arr1 + 2, arr1, 16);
    for (int i = 0; i < 10; i++)
    {
        printf("%d", arr1[i]);
    }
    return 0;
}

  • 1
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值