Cprogramming 简明教程

Error Handling in C

因此,C 编程并不直接支持错误处理,因为在 C 中没有可以防止错误或异常突然终止程序的关键字。但是,程序员可以使用其他函数进行错误处理。

您可以使用 errno 在 C 中高效地进行错误处理。此外,其他可用于错误处理的函数包括 perror, strerror, ferror,clearererr

The errno Variable

C 是一种系统编程语言。它以返回值的形式提供较底层的访问。如果发生任何错误,大多数 C 或甚至 Unix 函数调用将返回 -1 或 NULL,并设置错误代码 errno。它被设置为一个全局变量,并表示在任何函数调用期间发生的错误。您可以在 <error.h> 头文件中找到各种定义的错误代码。

因此,C 程序员可以检查返回的值,并可以根据返回的值采取适当的措施。这是一个好习惯,在初始化程序时将 errno 设置为 0。0 的值表示程序中没有错误。

下表显示了 errno 的值和与之关联的错误消息−

errno value

Error

1

Operation not permitted

2

没有此类文件或目录

3

No such process

4

Interrupted system call

5

I/O error

6

没有此类设备或地址

7

参数列表太长

8

Exec format error

9

Bad file number

10

No child processes

11

Try again

12

Out of memory

13

Permission denied

Example

请看以下示例:

#include <stdio.h>
#include <errno.h>

int main() {

   FILE* fp;

   // opening a file which does not exist
   fp = fopen("nosuchfile.txt", "r");
   printf("Value of errno: %d\n", errno);

   return 0;
}

它将生成如下输出:

Value of errno: 2

C 编程语言提供了 perror() 和 strerror() 函数,可用于显示与 errno 关联的文本消息。

The perror() Function

显示传递给它的字符串,后跟冒号、空格,然后是当前 errno 值的文本表示形式。

void perror(const char *str);

Example

在上面的示例中,“errno = 2”与消息 No such file or directory, 关联,可以使用 perror() 函数打印该消息

#include <stdio.h>
#include <errno.h>

int main(){

   FILE* fp;

   // opening a file which does not exist
   fp = fopen("nosuchfile.txt", "r");

   printf("Value of errno: %d\n", errno);
   perror("Error message:");

   return 0;
}

当你运行这段代码时,它将产生以下输出:

Value of errno: 2
Error message: No such file or directory

The strerror() Function

这将返回一个指向当前 errno 值的文本表示形式的指针。

char *strerror(int errnum);

让我们使用此函数显示 errno=2 的文本表示形式

Example

请看以下示例:

#include <stdio.h>
#include <errno.h>

int main() {

   FILE* fp;

   // opening a file which does not exist
   fp = fopen("nosuchfile.txt", "r");

   printf("Value of errno: %d\n", errno);
   printf("The error message is : %s\n", strerror(errno));

   return 0;
}
Value of errno: 2
he error message is : No such file or directory

The ferror() Function

此函数用于检查文件操作期间是否发生了错误。

int ferror(FILE *stream);

Example

在这里,我们尝试从以“w”模式打开的文件中读取。ferror() 函数用于打印错误消息

#include <stdio.h>

int main(){

   FILE *fp;
   fp = fopen("test.txt","w");
   char ch = fgetc(fp);  // Trying to read data, from writable file
   if(ferror(fp)){
      printf("File is opened in writing mode! You cannot read data from it!");
   }
   fclose(fp);

   return(0);
}

运行代码并检查其输出:

File is opened in writing mode! You cannot read data from it!

The clearerr() Function

clearerr() 函数用于清除文件流的末尾和错误指示符。

void clearerr(FILE *stream);

Example

请看以下示例:

#include <stdio.h>

int main(){

   FILE *fp;
   fp = fopen("test.txt","w");

   char ch = fgetc(fp);  // Trying to read data, from writable file

   if(ferror(fp)){
      printf("File is opened in writing mode! You cannot read data from it!\n");
   }

   // Clears error-indicators from the file stream
   // Subsequent ferror() doesn't show error
   clearerr(fp);

   if(ferror(fp)){
      printf("Error again in reading from file!");
   }
   fclose(fp);

   return(0);
}

Divide by Zero Errors

当对任何数字进行除法时,一个常见的问题是,程序员不会检查除数是否为 0,最终导致运行时错误。

Example 1

下面的代码通过在除法之前检查除数是否为 0 来修复此错误 -

#include <stdio.h>
#include <stdlib.h>

int main() {
   int dividend = 20;
   int divisor = 0;
   int quotient;

   if( divisor == 0){
      fprintf(stderr, "Division by zero! Exiting...\n");
      exit(-1);
   }
   quotient = dividend / divisor;
   fprintf(stderr, "Value of quotient : %d\n", quotient );
   exit(0);
}

编译并执行上述代码后,将产生以下结果 −

Division by zero! Exiting...
Program Exit Status

通常,在程序在成功操作后退出时,将使用 EXIT_SUCCESS 的值退出。此处,EXIT_SUCCESS 是一个宏,定义为 0。

Example 2

如果您的程序中存在错误条件并且您要退出,那么您应该以 EXIT_FAILURE 的状态退出,该状态定义为“ -1”。因此,我们按如下方式编写上述程序 -

#include <stdio.h>
#include <stdlib.h>

int main() {

   int dividend = 20;
   int divisor = 5;
   int quotient;

   if(divisor == 0) {
      fprintf(stderr, "Division by zero! Exiting...\n");
      exit(EXIT_FAILURE);
   }

   quotient = dividend / divisor;
   fprintf(stderr, "Value of quotient: %d\n", quotient );

   exit(EXIT_SUCCESS);
}

编译并执行上述代码后,将产生以下结果 −

Value of quotient: 4