一、什么是字符串函数
在C语言中,字符串函数也是非常重要的概念。它们提供了一系列函数来处理字符串,包括查找、替换、拼接、截取等。
其实,在C语言中我们本来想对字符串进行比较又或者是替换的一些操作的时候,我们不能像是比较两个整形一样那么的简单,这个时候借助string.h里面的库函数就很好的解决的了这些问题。
那么我们在使用这些库函数的时候应该也要想一下这些库函数是怎么实现这些相关的操作的,这样也更能提高我们的写代码水平。以下内容就是我对字符串函数模拟实现的一些心得跟大家分享一下。
二、字符串函数的模拟实现
首先,我们想要模拟实现一个库函数,我们首先就要先了解一下相关库函数的声明。我们要先去知道这个函数的参数、返回值以及实现这个函数的条件等等。下面是我对一些基本的字符串函数实现的心得。
1.strlen
size_t strlen ( const char * str );
strlen函数是用来计算字符串的长度的,它是以字符串中 ‘\0’ 作为结束标志,strlen函数返回的是在字符串中 ‘\0’ 前面出现的字符个数(不包
含 ‘\0’ )。
我们要模拟实现这个函数,首先,应该先传递给它一个字符串的起始地址,然后让起始地址一直加一个字符的位置,直到这个地址指向’\0’,这个时候,我们停止。此时,我们的返回值应该是地址增加的一个次数。
size_t my_strlen(const char* arr)
{
assert(arr);
size_t count = 0;
while (*arr)
{
arr++;
count++;
}
return count;
}
主函数:
int main()
{
char arr[] = "abcdefg";
int ret = my_strlen(arr);
printf("%d", ret);
return 0;
}
结果:
2.strcpy
char * strcpy ( char * destination, const char * source );
strcpy函数是用来将一个字符串拷贝到另一个字符串里面的。
模拟这个函数我们首先肯定是需要两个字符串的地址,一个是被拷贝的字符串,另一个是需要拷贝的字符串。有了这两个地址以后我们就可以直接把要拷贝的地址解引用赋值给待拷贝的地址里面,同时,两个地址往后面走,直到要拷贝的内容结束(也就是碰到了‘\0’)。
此时,在这里我们需要注意待拷贝的空间一定要大,否则,可能会出现越界访问,甚至是报错。
char* my_strcpy(char* p1, const char* p2)
{
assert(p2 && p1);
char* ret = p1;
while (*p1++ = *p2++)
{
;
}
return ret;
}
主函数:
int main()
{
char arr[20] = { 0 };
char arr1[20] = "hello world";
my_strcpy(arr, arr1);
printf("%s\n", arr1);
return 0;
}
结果:
3.strcmp
int strcmp ( const char * str1, const char * str2 );
strcmp函数是进行两个字符串的比较。我们都知道字符串并不能像是整形数字一样可以直接进行大小的比较,所以,借助这个函数我们就可以很容易的对两个字符串进行比较。
这个库函数的原理是先比较两个地址所对应字符的ASC||码的大小,如果第一位相同,那么就比下一位,直到碰到’\0’。因此这个函数也很好实现。
int my_strcmp(const char* p1, const char* p2)
{
assert(p1 && p2);
while (*p1 == *p2)
{
if (*p1 == '\0')
return 0;
p1++;
p2++;
}
return (*p1 - *p2);
}
主函数:
int main()
{
char arr1[] = "hello world";
char arr2[] = "victory";
if (my_strcmp(arr1, arr2) > 0)
printf(">");
else if (my_strcmp(arr1, arr2) < 0)
printf("<");
else
printf("=");
return 0;
}
结果:
4.strcat
char * strcat ( char * destination, const char * source );
strcat函数的作用是在字符串后面添加一串新的字符串。
这个函数的实现过程:如果我们要在字符串的后面添加新的字符串,我们首先就是要找到这个字符串的最后一位(即’\0’所对应的地址)。然后,将新的字符串首位赋值给’\0’,两地址往后走,直到新的字符串结束。
同时,在这里也要注意与strcpy一样的问题,我们首先要保证被添加的字符串可被修改,同时也要注意空间要大,不能造成越界访问。
char* my_strcat(char* dest, const char* source)
{
assert(dest && source);
char* ret = *dest;
while (*dest)
dest++;
while (*dest++ = *source++)
;
return ret;
}
主函数:
int main()
{
char arr1[40] = "hello world ";
char arr2[] = "victory";
my_strcat(arr1, arr2);
printf("%s\n", arr1);
return 0;
}
结果:
5.strstr
const char * strstr ( const char * str1, const char * str2 );
strstr函数它的作用是在一个字符串中查找指定的子字符串第一次出现的位置。
这个函数遇到第一种情况比较简单,比如"abcdef"跟"bcd",这种情况就是找到它们第一个相同的字符’b’然后向后比较就直接找到了,此时,第一次出现的位置就是第一个’b’.
第二种情况比这个稍微复杂一点,例如"abbcdef"跟"bcd",这种情况就是我们即使找到第一个b相同,但是子字符的第二位就跟长字符不同了,所以需要记录一下第一位相同时的位置(即b的位置)。
然后后面不同以后再跳回到相同的第一位的后一位进行比较,直到全部相同或者是长字符串结束(即遇到了’\0’)
const char* my_strstr(const char* p1, const char* p2)
{
assert(p1 && p2);
char* fir = p2;
while (*p1)
{
if (*p1 == *p2)
{
char* ret = p1;
while (*++p1 == *++p2 && *p2 != '\0' && *p1 != '\0')
{
;
}
if (*p2 != '\0')
{
p1 = ret;
p2 = fir;
}
else if (*p2 == '\0')
{
return ret;
}
}
p1++;
}
return NULL;
}
主函数:
int main()
{
char arr1[] = "victttory";
char arr2[] = "tory";
char* p = my_strstr(arr1, arr2);
printf("%s", p);
return 0;
}
结果:
6.实现库函数模拟所用到的const及assert解释
const这是一个关键字,用于声明一个常量变量。常量变量是在程序运行期间不能被修改的变量。
assert"assert"是一个用于调试和错误检查的关键字。它的作用是在程序执行过程中检查某个条件是否为真,如果条件为假,则会抛出一个异常或错误。
它在这里的作用就是防止函数里面传递空指针。
三、总结
以上内容就是我对这几个字符串函数模拟实现的心得,今天模拟实现的几个函数还是比较简单的,只要了解这个思路,我们以后模拟更复杂的函数也是可以做到的。当然,想要很好的模拟出来库函数的功能,我们一定要先去看库函数的声明。然后要去明白库函数使用什么方法去实现这些功能的。最后,根据库函数的声明我们知道了它需要什么参数返回什么内容再去进行模拟实现。
总的来说,实现方法可以不同,只要达到相同的效果就算是很好的实现了库函数的模拟。