linux下的c出错管理功能,Linux系统程序员的错误处理

程序员的错误处理

要把正确的搞定,也要把错误的搞定,还要防止别人有意无意的破坏;

主流的编程语言(除了C语言外)基本都使用异常机制处理错误,C语言中没有异常机制;

C程序员是用返回值代表是否出错,主要有以下4种情况:

1.如果返回类型是 int(如主函数/随机数等),并且返回值不可能是负数,正常数据会直接返回,用返回-1代表出错(如返回数组下标>=0);

2.如果返回类型是 int,并且返回值有可能是负数(如返回两个负数中的大者),此时正常数据用指针返回,返回-1代表出错,0代表正确;

3.如果返回类型是指针,返回 NULL 代表出错,其他代表正常;

4.如果函数不需要考虑出错问题,用 void 型函数,无返回值;

注意

以上4种情况只是经验之谈,大多如此;但不是绝对的;

如有时返回指针不用NULL而用-1表示出错((void*)-1))也是可以的;

一个函数影响外部数据的方式有2种:

1.用 return 语句返回;

2.参数中传递指针形式,也可以影响外部数据;

练习

有4个函数

a返回两个数的最大值,如果这两个数相等,返回错误;

/* 数据用指针传递,情况2 */

b返回0-10的随机数,如果随机数为0则函数返回错误;

/* 可以用-1表示出错,情况1 */

c传入一个字符串,如果传入的是"error",返回错误;否则返回原来函数的字符串;

/* 返回指针,情况3; */

d打印一个传入的字符串;

/* 不需要返回值,也无须考虑错误,情况4; */

/*

* 错误处理演示

*/

#include

#include

#include

#include

/* 情况1,正常值非负,用-1表示出错 */

int ran10() {

srand(time(0)); //设置种子防止伪随机

int ra = rand() % 11;

if (ra == 0) {

return -1;

}

return ra;

//返回-1代表出错,数据正常返回;

}

/* 情况2,正常值也有负数,返回0表示正常,数据用指针处理传递 */

int max(int num1, int num2, int *pi) {

if (num1 == num2) {

return -1; //相等则返回

}

*pi = (num1 > num2) ? num1 : num2;

return 0;

//0代表没有出错,数据存在*pi中

}

/* 情况3,返回值是指针类型,返回NULL代表出错,其他值直接带回 */

char *iserror(char *str) {

if (!strcmp(str, "error")) {

return NULL; //返回NULL代表错误

}

return str;

//返回指针

}

/* 情况4,不需要考虑出错问题,用void型函数; */

void print(char *str) {

printf("%s\n", str);

}

int main() {

int num = 0;

int r = max(-1, -2, &num);

if (r == -1) {

printf("error !\n");

} else {

printf("r = %d, max = %d\n", r, num);

}

r = ran10();

if (r == -1) {

printf("ran error \n");

} else {

printf("r = %d\n", ran10());

}

char *s = iserror("ok");

if (s == NULL) {

printf("iserror error !\n");

} else {

printf("%s\n", s);

}

print(s);

return 0;

}

C语言用外部的全局变量errno(error number)记录错误信息;

错误信息包括错误编号(int)和具体信息(字符串);

每个错误编号都对应一个具体信息;

errno存储的是错误编号;

函数strerror()/perror()/printf()用于错误信息的显示和转换;

char *strerror(int errnum)    传入一个编号,返回具体信息(转换函数);

void perror(const char *s)    不用传入错误编号,直接打印errno对应的信息(会自动换行);

printf("%m")    直接打印errno对应的信息;

不是所有的函数都使用errno处理错误,比如线程的函数;

注意安装翻译软件星际译王或goldendict

man命令可以查看命令/函数和头文件等的帮助信息;

如果man命令显示的不是英文,可以首先执行,export LANG="en";

在Linux中获取指令的帮助信息

man string.h

使用空格或Page Down翻页,也可使用上下键滚屏

在结果中可以使用搜索,n下一个,N上一个

q退出

man 3 printf    //查看C库函数

3表示的是man查找帮助的来源,可分为以下8种;

首先要查看概述,尤其注意其中的头文件和函数原型,参数类型,返回值类型;

然后查看描述信息,可以简要了解函数的功能;

最后还要看函数的返回值的意义;

man find

查找系统命令的帮助信息;

首先看name,了解命令的基本功能;

然后看概述,了解命令的使用形式;

然后再看描述,了解其具体功能;

然后还要看选项信息,了解各选项的意义;

如果可能还可以看一些使用范例;

不需要记住帮助信息,只需要明白使用的有价值的信息即可,用的多的自然就会记住常用的;

man man

The standard sections of the manual include

1   User Commands //用户命令

2   System Calls        //系统命令

3   C Library Functions    //C库函数

4   Devices and Special Files    //设备和特设文件

5   File Formats and Conventions    //文件格式与转换

6   Games et. Al.    //游戏等

7   Miscellanea    //杂集

8   System Administration tools and Deamons    //系统管理工具

man strerror

errno只有在出错时才会改变值,不出错也不会恢复值;

因此errno只能说明出过什么错,而不能据此判断当前步骤是否出错;

若判断是否出错要使用函数的返回值;

确定出错以后再使用errno判断出了什么错

/*

* perror()使用示例

*/

#include

#include

#include

int main() {

FILE *file = fopen("/etc/passwd1", "r");

if (file == NULL) { //判断是否出错

printf("[%d] %s\n", errno, strerror(errno));

perror("fopen 出错了");

//perror()会打印"参数: 错误信息"自动换行

//其中参数就是传给perror()的参数;

//函数出错基本都是使用perror(),线程一般不用perror()

printf("%m\n");

} else {

fclose(file);

}

file = NULL; //如果确保file不再使用可以省略;

return 0;

}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值