目录
1.strlen
2.长度不受限制的字符串函数
2.1strcpy
2.2strcat
2.3strcmp
3.长度受限制的字符串函数介绍
3.1strncpy
3.2strncat
3.3 strncmp
4.字符串查找
4.1strstr
4.2strtok
5 错误信息报告
5.1strerror
6.字符操作
注意事项:
(1)字符串已 '\0' 作为结束标志, strlen 函数返回的是在字符串中 '\0' 前面出现的字符个数(不包 含 '\0' )(2) 参数指向的字符串必须要以 '\0' 结束。(3)注意函数的返回值为 size_t ,是无符号的( 易错 )。
( 易错 )
针对 注意事项(3)完成以下例题
#include
int main()
{
const char* str1 = "abcdef";
const char* str2 = "bbb";
if (strlen(str2) - strlen(str1) > 0)
{
printf("str2>str1\n");
}
else
{
printf("srt1>str2\n");
}
return 0;
}
这是为什么呢?
就是因为strlen的返回值为size_t,是无符号的。
学会strlen函数的模拟实现
方法1:计算器方式
#include
int my_strlen(const char* p)
{
int count = 0;
while (*p)
{
count++;
p++;
}
return count;
}
int main()
{
char str[20] = "hello word";
int ret = my_strlen(str);
printf("%d\n", ret);
return 0;
}
方法2;指针相减法
#include
int my_strlen(const char* p)
{
char* p1 = p;
while (*p1)
{
p1++;
}
return p1-p;
}
int main()
{
char str[20] = "hello word";
int ret = my_strlen(str);
printf("%d\n", ret);
return 0;
}
方法3:递归法
#include
int my_strlen(const char* p)
{
if (*p == '\0')
{
return 0;
}
else
{
return 1 + my_strlen(p + 1);
}
}
int main()
{
char str[20] = "hello word";
int ret = my_strlen(str);
printf("%d\n", ret);
return 0;
}
注意事项:
(1)源字符串必须以 '\0' 结束。(2)会将源字符串中的 '\0' 拷贝到目标空间。(3)目标空间必须足够大,以确保能存放源字符串。(4)目标空间必须可变。
学会strcpy函数的模拟实现
#include
#include
char* my_strcpy(char* str1, const char* str2)
{
char* ret = str1;
assert(str1 && str2);
while (*str1++ = *str2++);
return ret;
}
int main()
{
char str1[20] = "hello word";
char str2[] = "abc";
my_strcpy(str1, str2);
printf("%s\n",str1 );
return 0;
}
注意事项:
(1)源字符串必须以 '\0' 结束。
(2)目标空间必须有足够的大,能容纳下源字符串的内容。
(3)目标空间必须可修改。
学会strcat函数的模拟实现
#include
#include
char* my_strcat(char* str1, const char* str2)
{
assert(str1 && str2);
char* ret = str1;
while (*str1)
{
str1++;
}
while (*str1++ = *str2++);
return ret;
}
int main()
{
char str1[20] = "hello word";
char str2[] = "abc";
my_strcat(str1, str2);
printf("%s\n",str1 );
return 0;
}
注意事项:
C语言规定strcmp的返回值返回一个正负数即可,不一定要返回1,-1,0但是在VS环境下则返回-1,0,1
学会strcmp函数的模拟实现
下面代码为返回值返回一个正负数
#include
#include
int my_strcmp(const char* str1, const char* str2)
{
assert(str1 && str2);
while (*str1 == *str2)
{
if (*str2 == '\0')
return 0;
str1++;
str2++;
}
return *str1 - *str2;
}
int main()
{
char str1[20] = "abc";
char str2[] = "abd";
printf("%d\n", my_strcmp(str1, str2));
return 0;
}
注意事项:
(1)拷贝 num 个字符从源字符串到目标空间。(2)如果源字符串的长度小于 num ,则拷贝完源字符串之后,在目标的后边追加'\ 0' ,直到 num 个
#include
#include
int main()
{
char str1[20] = "abcdef";
char str2[] = "xxx";
strncpy(str1,str2,3);
printf("%s\n", str1);
return 0;
}
超过要拷贝字符串的长度
#include
#include
int main()
{
char str1[20] = "abcdef";
char str2[] = "xxx";
strncpy(str1,str2,5);
printf("%s\n", str1);
return 0;
}
学会strncpy函数的模拟实现
#include
#include
char* my_strncpy(char* p1, const char* p2, size_t num)
{
assert(p1 && p2);
char* ret = p1;
while (num--)
{
if (*p2)
{
*p1 = *p2;
}
else
{
*p1 = '\0';
}
p1++;
p2++;
}
return ret;
}
int main()
{
char str1[20] = "abcdef";
char str2[] = "xxx";
my_strncpy(str1, str2, 5);
printf("%s\n", str1);
return 0;
}
#include
#include
int main ()
{
char str1[20];
char str2[20];
strcpy (str1,"To be ");
strcpy (str2,"or not to be");
strncat (str1, str2, 6);
puts (str1);
return 0;
}
学会strncat函数的模拟实现
#include
#include
#include
char* my_strncat(char* p1, const char* p2, size_t num)
{
assert(p1 && p2);
char* ret = p1;
while (*p1)
{
p1++;
}
while (num--&&*p2)
{
*p1 = *p2;
p1++;
p2++;
}
*(p1) = '\0';
return ret;
}
int main()
{
char str1[20];
char str2[20];
strcpy(str1, "To be ");
strcpy(str2, "or not to be");
my_strncat(str1, str2, 6);
puts(str1);
return 0;
}
#include
#include
int main()
{
char arr1[] = "abcqwertyuiop";
char arr2[] = "abcdef";
printf("%d\n", strncmp(arr1, arr2, 4));
return 0;
}
VS编译器
使用的例子
#include
#include
int main()
{
char str[] = "This is a simple string";
char* pch;
pch = strstr(str, "simple");
puts(pch);
return 0;
}
学会strstr函数的模拟实现
#include
#include
#include
char* my_strstr(const char* str1, const char* str2)
{
assert(str1 && str2);
char* cp = str1;
char* s1 = cp;
char* s2 = str2;
if (strlen(str2) > strlen(str1))
{
return NULL;
}
while (*cp)
{
s1 = cp;
s2 = str2;
while (s1 && s2 && *s1 == *s2)
{
s1++;
s2++;
}
if (*s2 == '\0')
{
return cp;
}
cp++;
}
return NULL;
}
int main()
{
char arr1[] = "abbbcdef";
char arr2[] = "bbc";
char* ret = my_strstr(arr1, arr2);
if (ret != NULL)
printf("%s\n", ret);
else
printf("找不到\n");
return 0;
}
图解:
sep 参数是个字符串,定义了用作分隔符的字符集合第一个参数指定一个字符串,它包含了 0 个或者多个由 sep 字符串中一个或者多个分隔符分割的标 记。strtok 函数找到 str 中的下一个标记,并将其用 \0 结尾,返回一个指向这个标记的指针。(注: strtok函数会改变被操作的字符串,所以在使用 strtok 函数切分的字符串一般都是临时拷贝的内容 并且可修改。)strtok 函数的第一个参数不为 NULL ,函数将找到 str 中第一个标记, strtok 函数将保存它在字符串 中的位置。strtok 函数的第一个参数为 NULL ,函数将在同一个字符串中被保存的位置开始,查找下一个标 记。如果字符串中不存在更多的标记,则返回 NULL 指针
#include
#include
int main()
{
char arr[] = "[email protected]@666#777";
char copy[30];
strcpy(copy, arr);
char sep[] = "@.#";
char* ret = NULL;
for (ret = strtok(copy, sep); ret != NULL; ret = strtok(NULL, sep))
{
printf("%s\n", ret);
}
return 0;
}
使用的例子
#include
#include
int main()
{
int i = 0;
for (i = 0; i < 10; i++)
{
printf("%d: %s\n", i, strerror(i));//
}
return 0;
}
errno
errno是C语言提供的一个全局变量,库函数在执行时发生了错误,会将错误码存放在errno中。
使用的例子
我们知道C语言中有一个文件操作的知识
第一步打开文件
第二步可以读或者写文件
第三步关闭文件
#include
#include
int main()
{
//C语言中可以操作文件
//操作文件的步骤
//1. 打开文件
//2. 读/写
//3. 关闭文件
FILE* pf = fopen("data.txt", "r");
if (pf == NULL)
{
printf("fopen: %s\n", strerror(errno));
//fopen: xxxxxx
return 1;
}
//读文件
//...
//关闭文件
fclose(pf);
return 0;
}
头文件都是"ctype.h"
使用的例子
#include
#include
int main ()
{
int i=0;
char str[]="Test String.\n";
char c;
while (str[i])
{
c=str[i];
if (isupper(c))
c=tolower(c);
putchar (c);
i++;
}
return 0;
以上为我个人的小分享,如有问题,欢迎讨论!!!