目录
一 前言
通过阅读这篇博客,博主会带你了解几个比较常用的库函数。利用库函数实现功能,可以帮助你简化自己的代码,上一篇详细介绍了strlen,因此此篇不再赘述。希望最后的模拟实现可以帮助你加深理解。
(以下这些库函数均可在这个网站查到: https://legacy.cplusplus.com/)
二 字符函数
1.1 strcpy
char * strcpy ( char * destination, const char * source );
-
strcpy函数的作用是将 source 指向的 C 字符串复制到 destination 指向的数组中,包括终止的空字符 ‘\0’(并在该点停止)。
-
为避免溢出,destination 指向的数组的大小应足够长,以包含与 source 相同的 C 字符串(包括终止的空字符),并且不应在内存中与 source 重叠。
-
试一下这个函数
#include <stdio.h>
#include <string.h>
int main()
{
char str1[] = "*****";
char str2[] = "acd";
printf("%s", strcpy(str1, str2));
return 0;
}
- 输出结果为
1.2 strcat
char * strcat ( char * destination, const char * source );
-
strcat的作用是将源字符串的副本附加到目标字符串。 目标中的终止空字符被源的第一个字符覆盖,并且在目标中两者连接形成的新字符串的末尾包含一个空字符。
-
试一下这个函数
#include <stdio.h>
#include <string.h>
int main()
{
char str1[10] = "abc";
char str2[] = "def";
printf("%s", strcat(str1, str2));
return 0;
}
- 输出结果为:
1.3 strcmp
int strcmp ( const char * str1, const char * str2 );
-
strcmp的作用是将 C 字符串 str1 与 C 字符串 str2 进行比较。
-
此函数开始比较每个字符串的第一个字符。 如果它们彼此相等,则继续以下对,直到字符不同或到达终止空字符。
-
此函数执行字符的二进制比较。
返回值 | 输入 |
---|---|
<0 | str1<str2 |
0 | str1=str2 |
>0 | str1>str2 |
- 试一下这个函数
#include <stdio.h>
#include <string.h>
int main()
{
char str1[] = "azsqc";
char str2[] = "azsq";
printf("%d", strcmp(str1, str2));
return 0;
}
- 运行结果
1.4 strncpy
char * strncpy ( char * destination, const char * source, size_t num );
-
这个函数将源字符串的前 num 个字符复制到目标。 如果在复制 num 个字符之前找到源 C 字符串的结尾(由空字符表示),则用零填充目标,直到总共写入了 num 个字符。
-
如果 source 长于 num,则不会在目标末尾隐式附加空字符。
-
运行程序
#include <stdio.h>
#include <string.h>
int main()
{
char str1[] = "*****";
char str2[] = "acd";
printf("%s\n", strncpy(str1, str2, 3));
printf("%s", strncpy(str1, str2, 4));
return 0;
}
-
输出为
-
除了strncpy还有strncat和strncmp,和此函数用法类似,各位可以试一试
1.5 strstr
const char * strstr ( const char * str1, const char * str2 );
char * strstr ( char * str1, const char * str2 );
-
此函数可以返回指向 str1 中第一次出现 str2 的指针,如果 str2 不是 str1 的一部分,则返回空指针。
-
让我们试一下
#include <stdio.h>
#include <string.h>
int main()
{
char str1[] = "azsdabcert";
char str2[] = "abc";
printf("%s", strstr(str1, str2));
return 0;
}
- 输出
1.6 strtok
char * strtok ( char * str, const char * delimiters );
-
简单来说str是我们想要处理的字符串,delimiters是一些符号,strtok可以通过delimiters中的符号将str分割成不同的部分。
-
在第一次调用时,该函数需要一个 C 字符串作为 str 的参数,其第一个字符用作扫描标记的起始位置。此函数具有记忆功能,在随后的调用中,给该函数一个空指针,strtok就可以将最后一个标记结束后的位置作为新的扫描起始位置。
-
如果不给空指针一直给新的字符串,那么就一直从给的字符串的开头开始扫描。
-
一旦在对 strtok 的调用中找到 str 的终止空字符,对该函数的所有后续调用(以空指针作为第一个参数)都将返回空指针。
-
记号的这一端会自动替换为空字符,并且记号的开头由函数返回。
-
使用这个函数
#include <stdio.h>
#include <string.h>
int main()
{
char str[] = "I,am.an,example";
char* p = strtok(str, ",.");
while (p != NULL)
{
printf("%s\n", p);
p = strtok(NULL, ",.");
}
return 0;
}
- 输出
2. 字符分类函数
函数 | 如果他的参数符合下列条件就返回真 |
---|---|
iscntrl | 任何控制字符 |
isdigit | 十进制数字 0~9 |
isxdigit | 十六进制数字,包括所有十进制数字,小写字母a-f,大写字母A-F |
islower | 小写字母a~z |
isupper | 大写字母A~Z |
- 类似函数还有很多,各位可以搜索一下
三 内存函数
1.memcpy
void * memcpy ( void * destination, const void * source, size_t num );
-
将 num 个字节的值从 source 指向的位置直接复制到 destination 指向的内存块。
-
源指针和目标指针指向的对象的底层类型与此函数无关
-
为了避免溢出,目标和源参数指向的数组的大小至少应为 num 字节,并且不应重叠(对于重叠的内存块,memmove 是一种更安全的方法)。
#include <stdio.h>
#include <string.h>
struct {
char name[40];
int age;
} person, person_copy;
int main ()
{
char myname[] = "Pierre de Fermat";
/* using memcpy to copy string: */
memcpy ( person.name, myname, strlen(myname));
person.age = 46;
/* using memcpy to copy structure: */
memcpy ( &person_copy, &person, sizeof(person) );
printf ("person_copy: %s, %d \n", person_copy.name, person_copy.age );
return 0;
}
2.memmove
void * memmove ( void * destination, const void * source, size_t num );
- 将 num 个字节的值从 source 指向的位置复制到 destination 指向的内存块。 复制就像使用中间缓冲区一样进行,允许目标和源重叠。
- memmove和memcpy非常相似,memmove更加强大,因为允许目标和源重叠
- 尝试使用
#include <stdio.h>
#include <string.h>
int main()
{
char arr[30] = "abcdefghijk";
memmove(arr + 3, arr, 6);
puts(arr);
return 0;
}
- 输出
3.memcmp
int memcmp ( const void * ptr1, const void * ptr2, size_t num );
-
将 ptr1 指向的内存块的前 num 字节与 ptr2 指向的前 num 字节进行比较,如果它们都相同则返回零,或者如果不匹配则返回一个不同于零的值,表示哪个更大。
-
请注意,与 strcmp 不同,该函数在找到空字符后不会停止比较。
#include <stdio.h>
#include <string.h>
int main ()
{
char buffer1[] = "DWgaOtP12df0";
char buffer2[] = "DWGAOTP12DF0";
int n;
n=memcmp ( buffer1, buffer2, sizeof(buffer1) );
if (n>0) printf ("'%s' is greater than '%s'.\n",buffer1,buffer2);
else if (n<0) printf ("'%s' is less than '%s'.\n",buffer1,buffer2);
else printf ("'%s' is the same as '%s'.\n",buffer1,buffer2);
return 0;
}
- 运行
四 模拟实现
1.模拟strcpy
#include <stdio.h>
char* my_strcpy(char* str1, char* str2);
int main()
{
char str1[] = "*****";
char str2[] = "acd";
printf("%s",my_strcpy(str1, str2));
return 0;
}
char* my_strcpy(char* str1, char* str2)
{
char* ret = str1;
while (*str1++ = *str2++)
{
;
}
return ret;
}
2.模拟strcat
#include <stdio.h>
char* my_strcat(char* str1, char* str2);
int main()
{
char str1[10] = "abc";
char str2[] = "def";
printf("%s", my_strcat(str1, str2));
return 0;
}
char* my_strcat(char* str1, char* str2)
{
char* ret = str1;
while (*str1 != '\0')
{
str1++;
}
while (*str1++ = *str2++)
{
;
}
return ret;
}
3.模拟strcmp
#include <stdio.h>
int my_strcmp(char* str1, char* str2);
int main()
{
char str1[] = "azsqc";
char str2[] = "azsq";
printf("%d",my_strcmp(str1, str2));
return 0;
}
int my_strcmp(char* str1, char* str2)
{
while (*str1 == *str2 && *str1 != '\0')
{
str1++;
str2++;
}
if (*str1 == '\0')
return 0;
if (*str1 > *str2)
return 1;
if (*str1 < *str2)
return -1;
}
4.模拟memcpy
#include <stdio.h>
char* my_memcpy(void* src, void* test, int num);
int main()
{
char src[] = "qwertq";
char test[20] = "zxcvbs";
printf("%s", my_memcpy(src, test, 6));
return 0;
}
char* my_memcpy(void* src, void* test, int num)
{
void* ret = test;//返回ret
while (num--)
{
*(char*) test = *(char*) src;
test = (char*)test+1;
src = (char*)src+1;
}
return ret;
}
5.模拟memmove
#include <stdio.h>
void* memmove(void* src, void* test, int num);
int main()
{
char src[] = "abcdefgh";
printf("%s", memmove(src, src + 3, 3));
return 0;
}
void* memmove(void* src, void* test, int num)
{
void* ret = test;
while (num--)
{
if (src < test)
{
*((char*)test + num) = *((char*)src + num);
}
if (src >= test)
{
*(char*)test = *(char*)src;
test = (char*)test + 1;
src = (char*)src + 1;
}
}
return ret;
}
五 最后
✨ 原创不易,还希望各位大佬支持一下 \textcolor{blue}{原创不易,还希望各位大佬支持一下} 原创不易,还希望各位大佬支持一下
👍 点赞,你的认可是我创作的动力! \textcolor{green}{点赞,你的认可是我创作的动力!} 点赞,你的认可是我创作的动力!
⭐️ 收藏,你的青睐是我努力的方向! \textcolor{green}{收藏,你的青睐是我努力的方向!} 收藏,你的青睐是我努力的方向!
✏️ 评论,你的意见是我进步的财富! \textcolor{green}{评论,你的意见是我进步的财富!} 评论,你的意见是我进步的财富!