前言
在使用C语言编写代码的时候不能使用类似Java的异常处理机制是非常难受的,所以今天放假用了一下午的时间简单实现了一下。
效果展示
先看一下示例程序:
#include "error/Error.h"
#define TEST_ERROR_1
#define TEST_ERROR_2
void func(int);
int main() {
try {
func(1);
} catch(TEST_ERROR_1) {
stdErr();
} catch(TEST_ERROR_2) {
stdErr();
} finally{
printf("finally\n");
};
return 0;
}
void func(int a)throws TEST_ERROR_1 TEST_ERROR_2 {
if (a == 1) {
throw Error(TEST_ERROR_1, "测试错误1");
} else if (a == 2) {
throw Error(TEST_ERROR_2, "测试错误2");
} else {
printf("无错误\n");
}
}
当给func
传入1、2、3
时控制台的输出如下:
实现原理
难点在于程序的跳转,通过宏定义和<setjmp.h>
就可以实现了,代码很少,一看就懂:
Error.h:
#ifndef DSA_ERROR_H
#define DSA_ERROR_H
#include <setjmp.h>
#include <stdlib.h>
#include <stdbool.h>
#include <string.h>
#include <stdio.h>
#define try if(!(setjmp(env)))
#define catch(TYPE) else if(strcmp(#TYPE,error.type)==0)
#define finally
#define throw
#define throws
#define Error(TYPE, MSG) do{error.type=#TYPE;error.msg=MSG;error.line=__LINE__;error.date=__DATE__;error.file=__FILE__;longjmp(env,1);}while(false)
struct Error {
char *type;
int line;
char *msg;
char *date;
char *file;
};
extern jmp_buf env;
extern struct Error error;
/**
* 控制台打印异常信息
*/
void stdErr();
#endif //DSA_ERROR_H
Error.c
#include "Error.h"
jmp_buf env;
struct Error error = {NULL, 0, NULL, NULL, NULL};
void stdErr() {
printf("%s %s %d %s\n", error.date, error.file, error.line, error.msg);
}
缺陷
由于C语言编译器不支持这种机制,所以当抛出一个异常但又不捕获的时候程序会在异常处终止但不会给出异常提示。