atexit() 與 exit()函數

函數exit()


函數原型:

 wKiom1diskGxc9mDAAAHqscUHgo576.png   

    exit()函數用於在程序運行的過程中隨時結束程序,exit的參數state將會返回給操作系統,返回0表示程序正常結束,非0表示程序非正常結束。main函數結束時也會隱式地調用exit函數。exit函數運行時首先會執行由atexit()函數登記的函數,然後會做一些自身的清理工作,同時刷新所有輸出流、關閉所有打開的流並且關閉通過標準I/O函數tmpfile()創建的臨時文件。

  exit() 結束當前進程/當前程序/,在整個程序中,只要調用 exit ,就結束;

 exit(1)表示進程非正常退出. 返回 1給操作系統;

 exit(0)表示進程正常退出. 返回 0給操作系統.

exit()和return的區別:

按照ANSI C,在最初調用的main()中使用return和exit()的效果相同。

但要注意這裏所說的是"最初調用"。如果main()在一個遞歸程序中,exit()仍然會終止程序;但return將控制權移交給遞歸的前一級,直到最初的那一級,此時return纔會終止程序。return和exit()的另一個區別在於,即使在除main()之外的函數中調用exit(),它也將終止程序。

函數_exit() 和 _Exit()--終止調用進程

函數原型:

wKiom1djTBWSlCJsAAA3TR58eq8199.png

函數描述和返回值:

wKioL1djUQOgWeGNAAB1319SLfI699.png

從中可以解讀道_Exit() is equivalent to _exit().(功能相同) 

exit與_exit的區別

頭文件:

exit:#include<stdlib.h>

_exit:#include<unistd.h>

_exit()函數:直接使進程停止運行,清除其使用的內存空間,並銷燬其在內核中的各種數據結構;

exit()函數則在這些基礎上作了一些包裝,在執行退出之前加了若干道工序。

exit()函數與_exit()函數最大的區別就在於 exit()函數在調用 exit 系統調用之前要檢查文件的打開情況,把文件緩衝區中的內容寫回文件。

atexit()函數--註冊程序正常終止時要被調用的函數

    按照ISO C的規定,一個進程可以登記多達32個函數,這些函數將由exit自動調用,通常這32個函數被稱爲終止處理程序,並調用atexit函數來登記這些函數。

    在程序退出時經常需要做一些諸如釋放資源的操作,但程序退出的方式有很多種。因此需要一種與程序退出方式無關的方法來進行程序退出時的必要處理。atexit()函數用來註冊程序正常終止時要被調用的函數。      


下面看一下atexit()函數的原型:

wKiom1djTXGyYAYLAAAuZX26PM8330.png

函數描述和返回值:

wKioL1djVdrTak5bAADbvDRTnog507.png

    atexit的參數是一個函數指針,當調用此函數時無須傳遞任何參數,該函數也不能返回值,atexit函數稱爲終止處理程序註冊程序,註冊完成以後,當函數終止時exit函數會主動的調用前面註冊的各個函數,但是exit函數調用這些函數的順序與這些函數登記的順序是相反的,我認爲這實質上是參數壓棧造成的,參數由於壓棧順序而先入後出。同時如果一個函數被多次登記,那麼該函數也將多次的執行。


代碼段:

#include<stdio.h>
#include<atdlib.h>

void fun1(void)
{
    printf("fun1\n");
}

void fun2(void)
{
    printf("fun2\n");
}

void fun3(void)
{
    printf("fun3\n");
}

int main()
{
    atexit(fun1);
    atexit(fun2);
    atexit(fun3);
    
    printf("main\n");
}

程序運行結果輸出是:

wKioL1dipGvA2xqnAAAkh2cp7v8009.png

    這些函數都是在main結束以後才被調用的。atexit只是註冊他們,使得他們在main結束以後被調用,看名字就可以看出來。



發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章