当前位置: 首页 > news >正文

C语言第九章字符函数和字符串函数

一.字符分类函数

   1.字符分类函数总览

    C语言规定字符有很多种类型,比如:数字字符,空白字符,转义字符等。当我们需要将这些不同类型的字符进行分类时,就应该了解C语言为我们提供的字符分类函数。下面对字符分类函数做进一步的了解。

字符分类函数概要
函数参数符合下列情况就返回真
iscntrl任何控制字符
isspace空白字符:空格:‘  ’,换页符:‘\f’,换行符:‘\n’,回车符:‘\r’,水平制表符:‘\t’,垂直制表符:‘\v’
isdigit十进制数字字符:0-9
isxdigit十六进制数字字符:0-9和A-F(a-f)
islower小写字母字符:a-z
isupper大写字母字符:A-Z
isalpha所有字母字符:a-z 和A-Z
isalnum字母或者数字字符:a-z 和A-Z和0-9
ispunct标点符号字符:任何不属于数字或字母的可打印图形字符
isgraph任何图形字符
isprint

任何可打印字符:包括图形字符和空白字符

2.字符分类函数详细解释

        字符分类函数使用时均需要包含头文件:<ctype.h>。字符分类函数都是依赖字符的ASCII码值进行字符的分类。上述多种字符分类函数的用法极为相似,下面给出全部函数的介绍:

        上述iscntrl函数的解释:函数参数为整型,返回类型也为整型。此函数的作用是:判断参数字符是否为控制字符(control character)。根据上方图片的解释,函数通过ASCII码值来判断参数字符是否为控制字符。当函数参数为控制字符时,函数返回真(非0整数);否则函数返回假0。

        上述isspace函数的解释:该函数参数类型为整型,且函数的返回类型也为整型。函数的作用是判读参数字符是否为空白字符。并且上述图片也举例了一些空白字符。函数参数为空白字符时,返回真(非0整数);否则函数返回假0。

        上述isdigit函数的解释:函数参数为和返回类型均为整型。该函数的作用为:判断参数字符是否为十进制数字字符。当函数参数为十进制数字字符时,函数返回真(非0整数);否则函数返回假0。

        上述isxdigit函数的解释:函数的参数和返回值的类型均为整型。该函数的作用:判断函数参数字符是否为十六进制的数字字符。在这里要知道十六进制的数字字符包括0-9、a-z、A-Z。如果函数参数字符为十六进制的数字字符,那么函数返回真(非0整数);否则函数返回假0。

        上述islower函数的解释:该函数的参数和返回值类型均为整型。该函数的作用是:判断函数参数字符是否为英语的小写字母字符。当将函数参数为英语小写字母字符时,函数返回真(非0整数);否则函数返回假0。下面的每个函数的作用顶部表格均有涉及,并且这些字符分类函数的用法极为相似,所以最后只举例一种字符分类函数的用法。

3.字符分类函数使用方法

        通过上述函数的详细解释,我们可以发现字符分类函数具有极大的相似之处。每个字符分类函数的参数和函数返回值类型都为整型。函数参数为整型的原因是为了得到需要判断字符的ASCII码值,通过与特殊字符的ASCII码值进行比较,从而达到判断字符类型的目的。函数返回值为整型的原因是:当字符满足该函数的判段的字符类型,则返回一个非0的整数;否则返回0。这样定义返回值,可以直观的得到判断结果。下面我们使用其中一个字符分类函数,作为例子来理解。

        题目要求:将给出的小写字符转换为大写,其他字符不变。

#include <stdio.h>
#include <ctype.h>    //调用字符分类函数需要的头文件
int main ()
{int i = 0;char str[] = "Test String.\n";    //定义需要转换的字符数组char c;while (str[i])    //当字符数组没有到字符串末尾时,循环继续{c = str[i];    if (islower(c))     //调用判断字符是否为小写的函数c -= 32;    //如果为小写,利用ASCII码值,将其转换为大写putchar(c);    //进行完上述操作,下面逐一进行字符的打印i++;}return 0;
}

        上述代码的具体解释:定义了字符串数组用于接下来的大小写转换,用while循环,当字符数组没到字符串结尾的\0时,循环一直进行,当进行到字符串末尾的\0时,循环终止。在循环的内部,先判断字符是否为小写,调用islower函数,灵活运用函数的返回值,当函数的返回值为非0值时,进行if语句,将小写转换为大写。当字符不为小写字母时,函数返回0,不进行ASCII码值的变换。最后逐一打印字符,完成题目的要求。

        在上述代码实践中,我们用的是ASCII码值进行字符的大小写转换,其实字符函数也有相关的字符转换函数,其作用就是字符的英语大小写转换。下面我们来学习字符转换函数:

二.字符转换函数

        在C语言中,总共为我们提供了两种字符转换函数。

int tolower ( int c );         //将参数传进去的大写字母转为小写字母

int toupper ( int c );         //将参数传进去的小写字母转为大写字母

        下面我们详细解释上述两字符转换函数:

        上述两个函数的参数部分和函数的返回值均为整型,函数参数部分是为了接收字符的ASCII码值,方便进一步进行大小写的转换。函数返回值是为了返回转换之后的字符ASCII码值,方便后续的使用。下面举字符转换函数的使用例子:

#include <stdio.h>
#include <ctype.h>    //调用字符分类和转换函数的头文件
int main ()
{int i = 0;char str[] = "Test String.\n";char c;while (str[i]){c = str[i];if (islower(c))         //判断该字符是否为小写c = toupper(c);    //当字符为小写时,调用字符转换函数,将小写转换为大写putchar(c);i++;}return 0;
}

        上述代码的具体解释:在字符分类函数的例子里,我们利用了ASCII码值进行大小写的转换。现在我们学习了字符转换函数,就可以直接使用 tolower 函数。从而达到预期的效果。

        这里需要注意的是:字符转换函数同样需要<ctype.h>头文件,在字符转换函数调用时,其本质是通过ASCII码值转换大小写的。

三.字符串函数

1.strlen函数的使用和模拟实现

       (1)函数的使用

        在原先的学习中,我们了解了字符串函数中的strlen,并且知道了该函数的两种模拟实现方法。下面将对strlen函数进行复习和深层次的理解。

        上述为strlen函数的图片介绍,根据上述图片得知:函数的参数类型为const char *;函数的返回值类型为无符号整型。函数参数类型经过const修饰,防止误将传来的字符串修改,char *类型指针接收字符串的首地址。函数的作用是从函数参数的地址处往后找 \0,找到后返回从字符串起始地址到 \0位置的字符串长度,因为是长度,所以函数的返回值是无符号整型。

        这里需要注意的是:字符串以 '\0' 作为结束标志,strlen函数返回的是在字符串中 '\0' 前面出现的字符个数(不包含 '\0' );参数指向的字符串必须要以 '\0' 结束; 注意函数的返回值为size_t,是无符号的( 易错 );strlen的使需要包含头文件<string.h>。

        下面举一个例题,强化一下对注意事项的理解:

#include <stdio.h>
#include <string.h>    //字符串函数需要的头文件
int main()
{const char* str1 = "abcdef";    //定义两个字符串const char* str2 = "bbb";if(strlen(str2)-strlen(str1)>0)    //利用strleen函数判断两者的大小,打印相关的信息{printf("str2>str1\n");} else{printf("srt1>str2\n");}return 0;
}

        上述代码的具体解释:明显的第一个字符串比第二个字符串要长一些,所以我们会认为上述代码的输出结果为srt1>str2,实际上述代码的输出结果为str2>str1。这是为什么呢?

        不要忘记了,strlen函数的返回类型为无符号整型,两个无符号整型类型的数据进行计算,得到的结果一定也是无符号整型。在上述代码中,字符串2的长度减去字符串1的长度结果为-3。但是我们要明白这里的-3应该是无符号整型。在系统中,数据存储的方式是以补码的形式,所以-3的补码为11111111 11111111 11111111 11111101。左侧32位数字就是-3的补码,但是现在被认为是无符号整型,那么首位的符号位就会被认为是数值位,这样原本结果应该是-3,现在却是一个特别大的整数,该数具体十六进制表示形式为:0xFFFFFFFD。可见此数非常之大。

(2)函数的模拟实现

        在先前的学习中,我们学习了两种strlen函数的模拟实现的方法,下面进行复习和更深层次的学习:

<1>方法一:计数器法
//计数器⽅式 
int my_strlen(const char * str)    //模拟实现strlen函数
{int count = 0;    //定义计数器assert(str);    //调用assert函数,防止函数参数指针为空while(*str)    //当函数参数不为 \0进入循环{    count++;    //每一次循环,计数器++str++;        //将指针指向的位置后移,直至移到 \0处}return count;
}

        上述strlen函数的实现手法为计数器法,从函数参数地址处开始,指针通过while循环的方式进行后移查找字符串末尾的 \0 ,直到找到 \0,函数返回计数器的数值。

<2>方法二:指针相减法
//指针-指针的⽅式 
int my_strlen(char *s)    
{assert(str);    //防止函数参数指针为空指针char *p = s;    //创建新的指针变量,用于循环中指针的移动while(*p != '\0' )p++;    //利用循环,将指针变量p进行后移,直至移到 \0的前面return p-s;        //返回两指针的差值
}        

        上述strlen函数的实现手法主要是运用了指针运算的法则,指针减法我们说过,当同类型指针相减时,得到的结果是两指针变量之间元素的个数。上述函数的实现中,通过创建新的指针变量,使函数参数的指针变量一直指向字符串的首地址,让创建的新指针变量进行后移,直至指向 \0前面的位置,最后函数返回两指针变量的差值。得到的结果就是字符串的长度。

<3>方法三:函数递归

        我们在不久前了解了函数递归的法则,现在我们可以尝试用函数递归的方法模拟实现该函数。

        根据上方图片的分析,我们可以知道:我们的my_strlen函数可以求出字符串的长度,求字符串长度时,当首字符不为 \0时,可以将此类大问题化为1+my_strlen(后面的字符串);当首元素为 \0时,函数返回0。

//不能创建临时变量计数器 
int my_strlen(const char * str)
{assert(str);        //防止str为空指针时解引用出现错误if(*str == '\0')        //当字符串开头为 \0时,函数返回0return 0;elsereturn 1 + my_strlen(str+1);    //当字符串不是 \0,则函数递归调用进一步求出字符串长度
}

        上方代码的具体解释:当字符串首字符为 \0时,函数返回0;当函数首字符不为 \0时,函数自己调用自己,进行函数递归,进一步求出字符串长度。

2.strcpy函数的使用和模拟实现

(1)函数的使用

        在C语言学习过程中,有时候需要对字符串进行遍历或者进行某些计算,但是我们不想将该字符串内的字符破坏掉。这时候就会再创建一个新的字符串,保存旧字符串的数值,这样就可以不用担心改掉原字符串的内容(可以随便霍霍了)。但是这样显然很麻烦,于是C语言为我们提供了字符串复制函数,下面我们一起来了解一下吧!

        根据上方图片得知,该函数的作用是:将字符串进行复制。函数的参数为两个 char *类型的变量,用于接收字符串的首地址;函数的返回值是char *,目的是返回复制好的字符串首地址,方便后续直接使用函数返回值,进行字符串的打印等之类的操作。

        这个函数需要注意的是:源字符串必须以 '\0' 结束,这样才能知道字符串是否复制完毕。会将源字符串中的 '\0' 拷贝到目标空间,方便后续对复制好的字符串进行直接的使用。  目标空间必须足够大,以确保能存放源字符串,防止因为空间不够导致程序报错。 目标空间必须可修改,否则就不可以将需要复制的字符串的值赋值给目标空间,进而达不到预期的效果。

(2)函数的模拟实现

char* my_strcpy(char *dest, const char*src)
{ char *ret = dest;    //创建指针变量保存字符串的首地址,防止因为计算而丢失首地址,这样就可以放心计算了assert(dest != NULL);        //防止两指针变量为空指针assert(src != NULL);while((*dest++ = *src++)){;}return ret;
}

        在上述代码中,while循环语句运用了较为高级的写法:将字符串内容和末尾的 \0一同复制给了目标空间。目标空间首位置指针和源头字符串首字符指针一同进行后移,在指针变量指向的位置后移同时进行了内容的赋值,最后当源头指针变量进行到 \0位置处时,因为是后置++,所以再进行最后的赋值,这样就达成了预期的效果:将源头字符串的内容和末尾的 \0进行复制到目标空间。

3.strcat函数的使用和模拟实现

(1)函数的使用

        该函数介绍:根据上述图片可以得出,该函数的作用是:将一个字符串追加到另一个字符串的后面。该函数的参数为两个char *类型的指针变量,用于接收两个字符串的首字符地址;该函数的返回类型为char *类型,方便后续直接使用返回值进行打印或其它操作。

        这个函数需要注意的是:源字符串必须以 '\0' 结束,否则找不到追加的起始位置。目标字符串中也得有 \0 ,否则没办法知道追加从哪里开始。目标空间必须有足够的大,能容纳下源字符串的内容 。目标空间必须可修改,

(2)函数的模拟实现

char *my_strcat(char *dest, const char*src)
{char *ret = dest;        //创建新的指针变量保存字符串的首地址,防止因计算数值变化而无法返回assert(dest != NULL);    //防止两指针为空指针assert(src != NULL);while(*dest)    //while循环,使dest指针指向\0的位置,方便后续字符串的覆盖{dest++;}while((*dest++ = *src++))    //进行字符串的追加{;}return ret;
}

        根据上述图片的解析:我们可以得出:实现该函数只需要将源字符串的内容覆盖在目标空间字符串末尾的 \0位置处即可,这里我们不要忘记还要将原字符串的末尾 \0覆盖过去。

        上述函数模拟实现的过程中,首先利用while循环找到目标空间字符串末尾的 \0,方便后续原字符串的覆盖,在找到末尾的 \0后,将原字符串复制到目标空间处(和strcpy函数实现的逻辑相同)。这样就完成了预期的效果:将原字符串追加到目标空间字符串的后面。

        这里我们有个疑问?字符串是否可以对自己使用该函数?

        首先dest指针会利用while循环找到该字符串的末尾 \0,然后src会覆盖掉目标空间的 \0,将src的内容逐步赋值给目标空间,但是因为src将 \0覆盖掉了,字符串末尾没有了 \0结尾,这样就会无限循环的进行追加,永不停息。这也是为什么原字符串末尾必须有 \0的原因。所以字符串不可以对自己使用该函数。

4.strcmp函数的使用和模拟实现

(1)函数的使用

        该函数的介绍:该函数的作用是判断两字符串的大小关系。函数的参数为 const char *类型,是为了接收字符串的首字符地址,并且防止修改数据;函数的返回值为整型,当第一个字符串大于第二个字符串,则函数返回大于0的数字;当第一个字符串小于第二个字符串,则函数返回小于0的数字;当两字符串相等时,函数返回数字0。

        此函数需要知道背后的原理,字符串的比较本质上比较的是每个字符的ASCII码值的大小。这里需要注意的是:该函数判断字符串的大小时,是逐一比较字符的ASCII码值,而不是比较字符串的长度。(也就是说:如果第一个字符串前面的字符ASCII码值比第二个字符串要大,那么第一个字符串就大于第二个字符串)。

        例如字符串一:ts;第二个字符串为:abcdef。明显的第二个字符串的长度比第一个字符串的长度要长,但是第一个字符串的首字符ASCII码值大于第二个字符串首字符的ASCII码值,所以第一个字符串大于第二个字符串。

(2)函数的模拟实现

int my_strcmp (const char * str1, const char * str2)
{int ret = 0 ;    assert(str1 != NULL);        //防止两指针为空指针assert(str2 != NULL);while(*str1 == *str2)    //当两指针解引用内容相同时,进入循环{if(*str1 == '\0')        //如果两指针的解引用内容均为\0,则说明两字符串相等,返回数字0return 0;str1++;        //如果不为\0,表示前面的字符相等,但是后面还没有比较,于是指针++str2++;}return *str1-*str2;        //当两指针解引用内容不同时,不进入循环,直接返回指针解引用内容的差值
}

        根据上述图片描述可得到,当两指针解引用相同时,进入while循环。当两指针解引用内容相同并且都为 \0,说明两字符串相同,则函数返回0;当两指针解引用内容相同,但是不为 \0时,将两指针指向的位置后移,判断下一个位置解引用的内容;当两指针解引用内容不相等时,不再进入while循环,直接返回两指针解引用内容的差值(刚好满足C语言规定的strcmp函数返回值的规则)。

5.strncpy函数的使用

        根据上面的图片解析可以得到该函数的作用是:将目标字符串的前num个字符复制到目标空间中。如果源字符串的长度小于num,则拷贝完源字符串之后,在目标的后边追加0,直到num个。该函数和strcpy函数极为类似,只是函数参数多了一个无符号整型,目的是控制复制字符串的字符个数。

6.strncat函数的使用

        根据上方的图片可以得出,该函数的作用是将将source指向字符串的前num个字符追加到destination指向的字符串末尾,最后再追加一个 \0 。如果source指向的字符串的长度小于num时,便会将字符串中到 \0 的全部内容追加到destination指向的字符串末尾。该函数和strncat函数类似,只不过多了一个num参数,为了控制追加字符的个数。

        下面举一个该函数使用的例子:

#include <stdio.h>
#include <string.h>
int main ()
{char str1[20];        //创建了两个字符串,但是没有初始化char str2[20];strcpy (str1,"To be ");    //调用strcpy函数,将第二个参数复制给str1strcpy (str2,"or not to be");        //调用strcpy函数,将第二个参数复制给str1strncat (str1, str2, 6);        //调用strncat函数,在str1后面追加str2字符串的前6个字符printf("%s\n", str1);    return 0;
}

        上方代码首先创建了两个没有进行初始化的字符串,然后调用strcpy函数,进行别样的初始化。(将"To be "复制给str1;将"or not to be"复制给str2),然后调用strncat函数,通过函数的参数可以得知,本代码的目的是将str2字符串前6个字符追加到str1字符串后。所以最后输出的内容为:To be or not。

7.strncmp函数的使用

        比较str1和str2的前num个字符,如果相等就继续往后比较,最多比较num个字母,如果提前发现不相等,就提前结束,大的字符所在的字符串大于另外⼀个。如果num个字符都相等,则函数返回数字0;如果前面的字符串大,则函数返回大于0的数字;如果后面的字符串大,则函数返回小于0的数字。该函数和strcmp函数相似,只不过多了num参数,为了控制比较字符串的范围。

8.strstr函数的使用和模拟实现

(1)函数的使用

        在C语言学习过程中,无论是数字还是字符串,我们都会遇到查找相关的问题。在一个给定的字符串查找另一个字符串。这种问题在学习过程中很常见,不错,strstr函数就是为了解决该问题而诞生的。下面我们进行该函数的学习。

        通过上方的图片可以得出,函数的参数为char *类型的,用于接收两个字符串的首字符的地址;函数的返回值依然是char *类型的,用于返回字符串str2在字符串str1中第一次出现的位置。字符串的比较匹配不包含 \0 字符,以 \0 作为结束标志。

        下面是该函数的使用举例:

#include <stdio.h>
#include <string.h>
int main ()
{char str[] ="This is a simple string";    //创建字符数组用于查找内容char * pch;    //定义指针变量,用于接收strstr函数的返回值pch = strstr (str,"simple");//调用strstr函数,在str找sample,并返回第一次在str数组找到位置处的指针strncpy (pch,"sample",6);    //调用strncpy函数将sample前6个字符复制到pch处printf("%s\n", str);    //打印字符数组现在的情况return 0;
} 

        上述代码的具体解释:首先创建了字符数组和指针变量,字符数组是需要查找内容的字符串,而指针变量是为了接收strstr函数的返回值。在上面调用strstr函数时,参数表明此次调用的目的是:在str字符串数组中找到字符串"simple",并且返回第一次在str数组找到时的地址。然后pch就是str数组的simple string字符串的首字符的地址。最后调用strncpy函数,让sample字符串的前6个字符复制到pch空间中,就会覆盖掉simple。最后打印str数组结果为:"This is a sample string"。

(2)函数的模拟实现

char * strstr (const char * str1, const char * str2)
{char *cp = (char *) str1;char *s1, *s2;if ( !*str2 )return((char *)str1);while (*cp){s1 = cp;s2 = (char *) str2;while ( *s1 && *s2 && !(*s1-*s2) )s1++, s2++;if (!*s2)return(cp);cp++;}return(NULL);
}

        上述代码的具体解释:当需要查找的字符串为空时,返回原字符串(对特殊情况的处理)。当需要查找的字符串不为空时,进入外层while循环,创建指针变量保存两字符串的首地址,方便后续计算,防止因为计算丢失字符串的首地址。当两指针不为空且两指针相等,则有可能匹配成功,两指针将指向的位置后移。一直到str2为空时,匹配成功,则返回第一次找到的指针cp。

        上述图片的例子,当第一次s1等于s2时,s1和s2继续向后移动,但是此时s1不等于s2了。不进入内层while循环,cp指针后移,继续进行下一次匹配。这时候通过了匹配,就返回保存的第一次查找到的str2首地址cp。

9.strtok函数的使用

        该函数的介绍:该函数的作用:在一个字符串中去掉包含另一个字符串内容的字符。函数第一个参数为已知的字符串,第二个函数参数为需要去掉的分隔符。函数的返回值为char *类型,返回指向当前子串的指针,若无可分割字串则返回NULL。

        delimiters参数指向一个字符串,定义了用作分隔符的字符集合。第一个参数指定一个字符串,它包含了0个或者多个由delimiters字符串中一个或者多个分隔符分割的标记。strtok函数找到str中的下一个标记,并将其用 \0 结尾,返回一个指向这个标记的指针。(注: strtok函数会改变被操作的字符串,所以被strtok函数切分的字符串一般都是临时拷贝的内容并且可修改。)strtok函数的第一个参数不为 NULL ,函数将找到str中第一个标记,strtok函数将保存它在字符串中的位置。 strtok函数的第一个参数为 NULL ,函数将在同一个字符串中被保存的位置开始,查找下一个标记。 如果字符串中不存在更多的标记,则返回 NULL 指针。

#include <stdio.h>
#include <string.h>
int main()
{char arr[] = "192.168.6.111";    //创建了字符数组,准备去掉其中的分隔符char* sep = ".";        //创建了需要分割的字符串数组char* str = NULL;    for (str = strtok(arr, sep); str != NULL; str = strtok(NULL, sep)){//通过for循环,分批次打印去掉分隔符的每个字符串printf("%s\n", str);}return 0;
}

        上述代码通过for循环,打印去掉分隔符的每个字符串。当第一个参数变为NULL时。循环停止,打印完毕。

        上述代码的输出结果为:

192

168

6

111

10.strerror函数的使用

        在我们书写代码时,难免会碰到一些问题,编译器报错会为我们提示这些问题所在,但是有些问题,编译通过了,但是没有报出问题所在,这个时候我们就需要strerror函数来接收错误信息了。

        strerror函数可以把得到参数部分错误码对应的错误信息的字符串地址。在不同的系统和C语言标准库的实现中都规定了一些错误码,一般是放在 errno.h 头文件中。C语言程序启动的时候就会使用一个全局的变量errno,来记录程序的当前错误码,只不过程序启动的时候errno的值是0,表示没有错误。当我们在使用标准库中的函数的时候发生了某种错误,就会将对应的错误码,存放在errno中,而一个错误码的数字是整数很难理解是什么意思,所以每一个错误码都是有对应的错误信息的。strerror函数就可以将错误对应的错误信息字符串的地址返回。

        下面我们尝试打印0-10错误码的错误信息:

#include <errno.h>
#include <string.h>
#include <stdio.h>
int main()
{int i = 0;for (i = 0; i <= 10; i++)     //利用循环,打印错误码为0-10的错误信息printf("%s\n", strerror(i));return 0;
}

在Windows11和VS2022环境下输出的结果如下:

No error

Operation not permitted

No such file or directory

No such process

Interrupted function call

Input/output error

No such device or address

Arg list too long

Exec format error

Bad file descriptor

No child processes

#include <stdio.h>
#include <string.h>
#include <errno.h>
int main ()
{FILE * pFile;        //创建文件流,用于接收下方操作的返回值pFile = fopen ("unexist.ent","r");    //打开文件,进行只读操作if (pFile == NULL)    //当文件不存在时,打印下方错误信息printf ("Error opening file unexist.ent: %s\n", strerror(errno));return 0;
}

Error opening file unexist.ent: No such file or directory

        也可以了解一下perror函数,perror函数相当于一次将上述代码中的第9行完成了,直接将错误信息打印出来。perror函数打印完参数部分的字符串后,再打印一个冒号和一个空格,再打印错误信息。所以可以理解perror=printf+strerror。

#include <stdio.h>
#include <string.h>
#include <errno.h>
int main ()
{FILE * pFile;pFile = fopen ("unexist.ent","r");if (pFile == NULL)perror("Error opening file unexist.ent");        //利用perror函数直接打印错误信息return 0;
}

Error opening file unexist.ent: No such file or directory

        上面分别展示了perror函数和strerror函数的使用,可以看出区别在于:perror函数可以直接将错误信息打印在屏幕上;而strerror函数可以得到错误信息的地址,可以进行打印等其它一系列操作。

http://www.dtcms.com/a/338861.html

相关文章:

  • Go语言快速入门指南(面向Java工程师)
  • 基于SpringBoot+Vue的养老院管理系统的设计与实现 智能养老系统 养老架构管理 养老小程序
  • 外网-内网渗透测试(文件上传漏洞利用)
  • MySQL事务篇-事务概念、并发事务问题、隔离级别
  • 链表基本运算详解:查找、插入、删除及特殊链表
  • 线段树结合矩阵乘法优化动态规划
  • 如何让你的知识分享更有说服力?
  • 云计算核心技术之云存储技术
  • 【React】简单介绍及开发环境搭建
  • JVM 面试精选 20 题(续)
  • react-quill-new富文本编辑器工具栏上传、粘贴截图、拖拽图片将base64改上传服务器再显示
  • 叉车结构设计cad+三维图+设计说明书
  • 浅看架构理论(一)
  • Parallels Desktop 26 技术预览版免激活下载适配Tahoe 26
  • 【撸靶笔记】第七关:GET - Dump into outfile - String
  • LeetCode算法日记 - Day 16: 连续数组、矩阵区域和
  • [系统架构设计师]信息系统架构设计理论与实践(十二)
  • 第八十四章:实战篇:图 → 视频:基于 AnimateDiff 的视频合成链路——让你的图片“活”起来,瞬间拥有“电影感”!
  • C++排序算法学习笔记
  • Java第十三课 异常(超简单)
  • 基于zephyr使用stm32的LTDC点亮ARGB8888LCD触摸屏
  • Kubernetes 简介
  • 代码随想录刷题——字符串篇(七)
  • 字符分类函数与字符转换函数
  • 【LeetCode 热题 100】279. 完全平方数——(解法一)记忆化搜索
  • kkfileview预览Excel文件去掉左上角的跳转HTM预览、打印按钮
  • Python爬虫第一课:爬取HTML静态网页小说章节
  • 国产!全志T113-i 双核Cortex-A7@1.2GHz 工业开发板—ARM + FPGA通信案例
  • PicoShare 文件共享教程:cpolar 内网穿透服务实现跨设备极速传输
  • Simulink库文件创建及使用方法