尝试模拟常用string.h中的库函数

发布于:2022-12-14 ⋅ 阅读:(407) ⋅ 点赞:(0)

尝试模拟常用string.h中的库函数

当我们解决问题的时候,常常会使用一些特别的库函数,这些库函数的出现,大大的方便了我们解决问题,也增加了解题的速度,这些库函数的使用让我们的代码更加简便,易读性也随之提高。既然库函数有这么多好处,我们更应该学会它们的实现一些库函数的方法,这样才能让我们学得更加深刻,使用起来如鱼得水。

这里特别介绍一个assert函数,该函数是用于测试指针是否为空,如果为空返回错误结果,否则为真。

strlen库函数实现

strlen函数是用于求字符串长度的,返回的结果是\0之前的字符个数。

#include<assert.h>
int my_strlen(char* dest)
{
    assert(dest);
    int count=0;//计数器
    while(dest++)
    {
        count++;
    }
    return count;//返回计数器
}

这个库函数的自我实现方法有很多种,比如使用下标法,也可以返回他的元素个数,要注意判断该字符串是否为空,然后再进行计数。

strcpy模拟实现

strcpy函数是将sour中的字符串包括\0都拷贝放在dest,然后返回dest。

#include<assert.h>
int* my_strcpy(char* dest,const char* sour)
{
    assert(dest&&sour);
    char* ret=dest;
	while(*sour!=='\0')
	{
		*(dest++)=*(sour++);
	}
    *dest='\0';//最后一个字符串要改为‘\0’
	return ret;
}

这个函数要注意不能把\0丢掉,还有很多种方法可以实现,比如走一步拷贝一个字符判断条件为sour不能为\0。

strcmp模拟实现

该函数主要用于比较两个字符串的大小,如果str1大则返回大于1的数字,如果srtr2大则返回小于0的数字。

#include<assert.h>
int my_strcmp(const char* str1, const char* str2)
{
	assert(str1&&str2);
	int flag = 0;
	while(*str1!='\0'&&str2!='\0')
	{
		if (*str1 != *str2)//字符不同,退出计算
		{
			break;
		}
		str1++;
		str2++;
	}
	return *str1-*str2;//相同返回0,不同比较返回结果
}

实现这个函数需要注意把返回值设置好,然后在合适的条件下进行比较返回。

strccat模拟实现

该函数作用是在原来的字符串后面追加一个字符串,这里要注意是在原来的字符串的\0的位置开始,返回值是追加好的字符串。

#include<assert.h>
char* my_strcat(char* dest,const char* sour)
{
	assert(dest&&sour);
	char* ret = dest;//设置返回字符串
	while(*dest)//定位\0
	{
		dest++;
	}
	while (*(dest++) = *(sour++))//开始交换
	{
		;
	}
	return ret;
}

要先找到\0的位置,然后进行交换。

strstr模拟实现

该库函数是用来找出字串的,如果str2是str1的字串返回字串开始的位置,如果不是返回空。

#include<assert.h>
const char* my_strstr(const char* str1, const char* str2)
{
	const char* ret = str1;//设立可能的返回值
	while (*ret != '\0')
	{
		const char *p1 = ret;//定位开始
		const char* p2 = str2;
		while(*p1 == *p2)//都为0自动退出循环
		{
            //开始比较
			*p1++;
			*p2++;
		}
		if (*p2 == '\0')//str2的结束标志,说明str2为str1的子串
			return ret;
		ret++;
	}
	return NULL;
}

该函数要控制每一个字符都可能是str2的开始,所以要每一个可能都过滤一遍。

似乎有点意犹未尽,所以这里再介绍两个内存库函数!!

memcpy模拟实现

该函数是将内存中的字节一个一个进行拷贝,和strncpy有异曲同工之妙,但是strncpy只用于字符串,memcpy是用于所有的数据类型,不管你是什么数据类型,都可以拷贝完成。

#include<assert.h>
void * my_memcpy(void* dest, void* sour, size_t num)//void* 是返回值
{
	assert(dest&&sour);
	void* ret = dest;//设置返回值
	while (num--) 
	{
		*(char*)dest = *(char*)sour;//拷贝
		dest = (char*)dest + 1;//向后面的字节遍历
		sour = (char*)sour + 1;
	}
	return ret;
}

这个函数和strncpy十分相似,都是用控制数来控制拷贝的字符数。

memmove模拟实现

该函数是用于拷贝字符串,还可以将本身字符串进行移动拷贝,当使用其他字符串进行自身拷贝时,会发生一些无法控制的错误,为了解决自我拷贝的问题,这个函数巧妙的完成了该项功能。

#include<assert.h>
void *my_memmove(void *dest, const void *src, size_t num)
{
	void* ret = dest;
	if (src > dest)//当需要位移地址在目标地址后面,使用从前向后法则
	{
		while (num--)
		{
            //拷贝
			*(char*)dest = *(char*)src;
			dest = (char*)dest + 1;
			src = (char*)src + 1;
		}
	}
	else//当需要位移的首元素地址在目标地址前面,使用从后向前法则
	{
		while (num--)
		{
			*((char*)dest + num) = *((char*)src + num);//拷贝
		}
	}
	return ret;
}

这里要注意前面的元素是放在低地址处,后面的是放在高地址处,比较地址大小然后决定使用那个方法。

今天的分享就到这里,希望多多指点,一起向前。

本文含有隐藏内容,请 开通VIP 后查看

网站公告

今日签到

点亮在社区的每一天
去签到