吾爱程序员:这里有好玩的游戏和软件
当前位置:首页C语言教程 → exit(), abort() 和 assert()

exit(), abort() 和 assert()

来源:网络 | 更新时间:2022-01-14 21:54:21
exit()
void exit ( int status ); 
exit() 正常终止进程。 status:返回给父进程的状态值。通常,状态值为 0 或 EXIT_SUCCESS 表示成功,任何其他值或常量 EXIT_FAILURE 用于表示错误。exit() 执行以下操作。 * 刷新未写入的缓冲数据。 * 关闭所有打开的文件。 * 删除临时文件。 * 返回一个整数退出状态给操作系统。 C 标准atexit()函数可用于自定义 exit() 以在程序终止时执行其他操作。 exit的使用示例。
/* exit example */
#include <stdio.h>
#include <stdlib.h>

int main ()
{
FILE * pFile;
pFile = fopen ("myfile.txt", "r");
if (pFile == NULL)
{
printf ("Error opening file");
exit (1);
}
else
{
/* file operations here */
}
return 0;
}
当调用 exit() 时,属于该进程的所有打开的文件描述符都将关闭,并且该进程的任何子进程都由进程 1 init 继承,并且进程父进程会收到一个 SIGCHLD 信号。 exit() 背后的奥秘在于它只需要 0 – 255 范围内的整数参数。超出范围的退出值可能会导致意外退出代码。大于 255 的退出值返回退出代码模 256。 例如,退出 9999 给出退出代码 15 即 (9999 % 256 = 15)。 下面是说明上述事实的 C 实现:
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/wait.h>

int main(void)
{
pid_t pid = fork();

if ( pid == 0 )
{
exit(9999); //passing value more than 255
}

int status;
waitpid(pid, &status, 0);

if ( WIFEXITED(status) )
{
int exit_status = WEXITSTATUS(status);

printf("Exit code: %dn", exit_status);
}

return 0;
}
输出:
Exit code: 15
请注意,由于禁用了 fork(),上述代码可能不适用于在线编译器。 解释:这是 8 位整数溢出的影响。在 255(所有 8 位设置)之后为 0。 因此输出为“退出代码模 256”。上面的输出实际上是值 9999 和 256 的模数,即 15。 abort()
void abort ( void );
与 exit() 函数不同,abort() 可能不会关闭打开的文件。它也可能不会删除临时文件,也可能不会刷新流缓冲区。此外,它不会调用用atexit()注册的函数。 该函数实际上通过引发 SIGABRT 信号来终止进程,并且您的程序可以包含一个处理程序来拦截该信号(请参阅this)。 所以像下面这样的程序可能不会将“Geeks for Geeks”写入“tempfile.txt”
#include<stdio.h>
#include<stdlib.h>
int main()
{
FILE *fp = fopen("C:\myfile.txt", "w");

if(fp == NULL)
{
printf("n could not open file ");
getchar();
exit(1);
} 

fprintf(fp, "%s", "Geeks for Geeks");

/* ....... */
/* ....... */
/* Something went wrong so terminate here */ 
abort();

getchar();
return 0; 
} 
如果我们想确保将数据写入文件和/或刷新缓冲区,那么我们应该使用 exit() 或包含 SIGABRT 的信号处理程序。 assert()
void assert( int expression );
如果表达式计算结果为 0(假),则表达式、源代码文件名和行号被发送到标准错误,然后调用 abort() 函数。如果标识符 NDEBUG(“无调试”)是用#define NDEBUG 定义的,那么宏断言什么也不做。 常见的错误输出形式为: Assertion failed: expression, file filename, line line-number
#include<assert.h>

void open_record(char *record_name)
{
assert(record_name != NULL);
/* Rest of code */
}

int main(void)
{
open_record(NULL);
}
 

最新文章

热点资讯

手游排行榜

CopyRight 2020-2030吾爱程序员

鄂ICP备2021004581号-8

本站资源收集于网络,如有侵权请联系我们:35492删除0109@qq.com