wait( )和 waitpid( )

進程一旦調用了wait,就立即阻塞自己,由wait自動分析是否當前進程的某個子進程已經退出,如果讓它找到了這樣一個已經變成僵尸的子進程,wait就會收集這個子進程的信息,并把它徹底銷毀后返回;如果沒有找到這樣一個子進程,wait就會一直阻塞在這里,直到有一個出現為止。

#include <sys/types.h> 
#include <sys/wait.h>pid_t wait(int *status) 

參數status用來保存被收集進程退出時的一些狀態,它是一個指向int類型的指針。但如果我們對這個子進程是如何死掉的毫不在意,只想把這個僵尸進程消滅掉,(事實上絕大多數情況下,我們都會這樣想),我們就可以設定這個參數為NULL
如果成功,wait會返回被收集的子進程的進程ID,如果調用進程沒有子進程,調用就會失敗,此時wait返回-1,同時errno被置為ECHILD。
下面是范例:

int main()
{pid_t pid = fork();switch (pid){case -1:perror ("fork");break;case 0:                 // 子進程printf ("我是子進程,我的ID是%d\n", getpid());sleep (3);exit (0);default:                // 父進程printf ("等待子進程掛掉\n");sleep (3);pid_t childId = wait (NULL);printf ("成功處理一個子進程,該子進程是:%d\n", childId);sleep (3);break;}return 0;
}

運行后發現,3秒鐘的等待時間,這就是我們設定的讓子進程睡眠的時間,只有子進程從睡眠中蘇醒過來,它才能正常退出,也就才能被父進程捕捉到。其實這里我們不管設定子進程睡眠的時間有多長,父進程都會一直等待下去。

數status:如果參數status的值不是NULL,wait就會把子進程退出時的狀態取出并存入其中,這是一個整數值(int),指出了子進程是正常退出還是被非正常結束的(一個進程也可以被其他進程用信號結束,我們將在以后的文章中介紹),以及正常結束時的返回值,或被哪一個信號結束的等信息。由于這些信息被存放在一個整數的不同二進制位中,所以用常規的方法讀取會非常麻煩,人們就設計了一套專門的宏(macro)來完成這項工作,下面我們來學習一下其中最常用的兩個:

1,WIFEXITED(status)這個宏用來指出子進程是否為正常退出的,如果是,它會返回一個非零值。

(請注意,雖然名字一樣,這里的參數status并不同于wait唯一的參數–指向整數的指針status,而是那個指針所指向的整數,切記不要搞混了。)

2, WEXITSTATUS(status)當WIFEXITED返回非零值時,我們可以用這個宏來提取子進程的返回值,如果子進程調用exit(5)退出,WEXITSTATUS(status)就會返回5;如果子進程調用exit(7),WEXITSTATUS(status)就會返回7。請注意,如果進程不是正常退出的,也就是說,WIFEXITED返回0,這個值就毫無意義。
實例:

// status保存了被收集進程退出時的一些狀態
int main()
{pid_t pid = fork();switch (pid){case -1:perror ("fork");break;case 0:                 // 子進程printf ("我是子進程,我的ID是%d\n",getpid());while (1);exit (0);default:                // 父進程printf ("等待子進程掛掉\n");int status;pid_t childId = wait (&status);printf ("成功處理一個子進程,該子進程是:%d %d\n", childId, status);if (WIFEXITED(status)){printf ("正常死亡\n");}else{printf ("被人做掉\n");}break;}return 0;
}

利用kill 殺死子進程。
這里寫圖片描述

這里寫圖片描述

wait一次只能處理一個僵尸進程:

// wait一次只能處理一個僵尸進程
int main()
{int count = 10;while (count--){pid_t pid = fork();switch (pid){case -1:perror ("fork");break;case 0:             // 子進程printf ("我是子進程,我的ID是%d\n", getpid());sleep (3);exit (0);default:            // 父進程break;}}printf ("等待子進程掛掉\n");while (1){pid_t childId = wait(NULL);if (-1 == childId){break;}printf ("成功處理一個子進程,該子進程是:%d\n", childId);}return 0;
}

這里寫圖片描述


#include <sys/types.h> 
#include <sys/wait.h>pid_t waitpid(pid_t pid,int *status,int options)

從本質上講,系統調用waitpid和wait的作用是完全相同的,但waitpid多出了兩個可由用戶控制的參數pid和options,從而為我們編程提供了另一種更靈活的方式。下面我們就來詳細介紹一下這兩個參數:

pid
從參數的名字pid和類型pid_t中就可以看出,這里需要的是一個進程ID。但當pid取不同的值時,在這里有不同的意義。

pid>0時,只等待進程ID等于pid的子進程,不管其它已經有多少子進程運行結束退出了,只要指定的子進程還沒有結束,waitpid就會一直等下去。
pid=-1時,等待任何一個子進程退出,沒有任何限制,此時waitpid和wait的作用一模一樣。
pid=0時,等待同一個進程組中的任何子進程,如果子進程已經加入了別的進程組,waitpid不會對它做任何理睬。
pid<-1時,等待一個指定進程組中的任何子進程,這個進程組的ID等于pid的絕對值。

options
options提供了一些額外的選項來控制waitpid,目前在Linux中只支持WNOHANG和WUNTRACED兩個選項,這是兩個常數,可以用”|”運算符把它們連接起來使用
WNOHANG: 如果沒有任何已經結束的子進程則馬上返回,不予以等待。
WUNTRACED :如果子進程進入暫停執行情況則馬上返回,但結束狀態不予以理會。

返回值:如果執行成功則返回子進程識別碼(PID),如果有錯誤發生則返回-1。失敗原因存于errno中。

int main()
{pid_t pid = fork();switch (pid){case -1:perror ("fork");break;case 0:                     // 子進程printf ("我是子進程,我的ID是%d\n", getpid());while (1);exit (0);default:                    // 父進程printf ("等待子進程掛掉\n");int status;pid_t childId = waitpid (-1, NULL, WNOHANG);printf ("成功處理一個子進程,該子進程是:%d, %d\n", childId, status);break;}return 0;
}

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/448471.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/448471.shtml
英文地址,請注明出處:http://en.pswp.cn/news/448471.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

享受閱讀的十二個好習慣

嚴謹的國際閱讀率比較研究顯示&#xff0c;當下韓國國民人均閱讀量約為每年11本&#xff0c;法國約為8.4本&#xff0c;日本在8.4—8.5本之間。全世界每年閱讀書籍數量排名第一的是猶太人&#xff0c;平均每人一年讀書64本。而中國13億人口&#xff0c;扣除教科書&#xff0c;平…

在 vscode 中使用 Git :拉取、提交、克隆

前些天發現了一個巨牛的人工智能學習網站&#xff0c;通俗易懂&#xff0c;風趣幽默&#xff0c;忍不住分享一下給大家。點擊跳轉到教程。 PS&#xff1a;轉載此文后&#xff0c;網友在評論中提到還有其它方法&#xff0c;不過目前個人尚在研究中&#xff0c;有興趣的朋友們也可…

偶也要去上海Tech一把了

公司組織的&#xff0c;后天去&#xff0c;呵呵&#xff1a;&#xff09;希望能多認識一點博客園的兄弟姐妹轉載于:https://www.cnblogs.com/martinxj/archive/2004/09/14/42930.html

進程控制常用的一些操作

1、獲取進程的id int main0() {printf ("當前進程 ID %d\n", getpid());printf ("當前父進程&#xff1a;%d\n", getppid());printf ("當前用戶&#xff1a; %d\n", getuid());while (1);return 0; }2、fork 和 vfork之前的博客里有&#xf…

vscode 配置 git (配置、暫存、推送、拉取、免密)

前些天發現了一個巨牛的人工智能學習網站&#xff0c;通俗易懂&#xff0c;風趣幽默&#xff0c;忍不住分享一下給大家。點擊跳轉到教程。 vscode 中對 git 進行了集成&#xff0c;很多操作只需點擊就能操作&#xff0c;無需寫一些 git 指令。 不過這就需要你對 vscode 進行配…

男女之間應該保留多少隱私

究竟&#xff0c;男女朋友之間&#xff0c;應該保留多少個人隱私? 我覺得&#xff0c;如果各自的隱私太多,那么&#xff0c;很難會相信彼此的愛能有多深濃。然而&#xff0c;如果兩個人沒有半點隱私,而且絕對坦誠。 彼此的行為和思想也沒有絲毫隱瞞的話,這種清白赤誠有如標…

處理bugs心法

1. 前提 第一層&#xff1a;遇到異常首先必須告訴自己&#xff0c;冷靜&#xff0c;不要慌。&#xff08;一看到Bug就心慌&#xff0c;那么武功就施展不了了&#xff09; 2. 入門級 第二層&#xff1a;遇到Bug&#xff0c;第一潛意識看輸出異常的信息的&#xff08;控制臺輸出&…

C語言實現簡單的電子通訊錄2

這兩天學完系統調用和標準IO&#xff0c;之前的通訊錄可以進行一些改進&#xff0c;將數據保存到文件中(圖我這里就不發了)。 原理&#xff1a;每次啟動程序時先從預設文件中以只讀的形式讀取保存的通訊錄信息&#xff0c;然后將讀取到的信息導入到結構體中&#xff1b;每次執…

解決 VS Code 保存時候自動格式化

前些天發現了一個巨牛的人工智能學習網站&#xff0c;通俗易懂&#xff0c;風趣幽默&#xff0c;忍不住分享一下給大家。點擊跳轉到教程。 不知道從哪個版本起&#xff0c;VS code 保存會自動格式化。 以前都是altshiftF格式化的&#xff0c;現在一保存就格式化&#xff0c;而…

發布在線文檔【軟件=業務+架構+流程+組織.pptx】

10年的技術工作&#xff0c;軟件這個詞對我來說一點都不陌生&#xff0c;但是當我問自己如何理解軟件的&#xff1f;我卻不知道如何回答。軟件&#xff1d;業務&#xff0b;架構&#xff0b;流程&#xff0b;組織&#xff0c;其中公式是借用軟件產品線工程BAPO的概念&#xff0…

12種食物最養男人 10種食物最養女人 太值得收藏了

據統計&#xff0c;男性10大死因中有4項與飲食有關&#xff0c;包括癌癥、腦血管疾病、心臟病和糖尿病。以下12種食品對男性健康有益&#xff0c;建議男性多多攝取。 男人需要的十種養生食物 No.1西紅柿 西紅柿的酸味能促進胃液分泌&#xff0c;幫助消化蛋白質等&#xff…

ES 基礎

1. ES 基礎一網打盡 1.1 ES定義 ESelaticsearch簡寫&#xff0c; Elasticsearch是一個開源的高擴展的分布式全文檢索引擎&#xff0c;它可以近乎實時的存儲、檢索數據&#xff1b;本身擴展性很好&#xff0c;可以擴展到上百臺服務器&#xff0c;處理PB級別的數據。 Elasticsear…

為什么 那么多 前端開發者都想學 Vue.js

根據JavaScript 2017 前端庫狀況調查 Vue.js是開發者最想學的前端庫。我在這里說明一下我為什么認為這也是和你一起通過使用 Vue 構建一個簡單的 App 應用程序的原因。 我最近曾與 Evan You&#xff0c;Chris Fritz&#xff0c;Sarah Drasner&#xff0c;和 Adam Jahr 做了一個…

進程間通信之管道通信

兩個程序之間傳遞數據的一種簡單方法是使用popen和pclose。 #include <stdio.h> FILE *popen(const char *command, const char *type); int pclose(FILE *stream); popen函數允許一個程序將另一個程序作為新進程來啟動&#xff0c;并可以傳遞數據給它或者通過它接收數據…

vue 各組件 使用 Demo

環境搭建 前些天發現了一個巨牛的人工智能學習網站&#xff0c;通俗易懂&#xff0c;風趣幽默&#xff0c;忍不住分享一下給大家。點擊跳轉到教程。 假設你已經通讀vue官方文檔&#xff08;文檔都沒讀一遍&#xff08;至少&#xff09;&#xff0c;那不建議動手擼碼&#xff…

Dropbox推獨立應用,公司估值已達100億美元

摘要&#xff1a;Dropbox剛獲得5億美元的新一輪融資&#xff0c;其估值已高達100億美元&#xff0c;現在又推出針對云服務的獨立應用Carousel&#xff0c;不久之后&#xff0c;還會有應用陸續推出&#xff0c;隨著美國前國務卿賴斯的加盟&#xff0c;Dropbox在云市場的表現異常…

SQL經典面試題(二)

有3個表S&#xff0c;C&#xff0c;SCS&#xff08;SNO&#xff0c;SNAME&#xff09;代表&#xff08;學號&#xff0c;姓名&#xff09; //主鍵&#xff1a;SNO //多個人&#xff0c;多門課 3張表 &#xff0c;SC 關系表C&#xff08;CNO&#xff0c;CNAME&#xff0c;…

進程間通信之信號he信號量

信號的篇幅較少&#xff0c;就把他和信號量放在一起了。先講講他們之間的區別&#xff1a; 1.信號&#xff1a;&#xff08;signal&#xff09;是一種處理異步事件的方式。信號時比較復雜的通信方式&#xff0c;用于通知接受進程有某種事件發生&#xff0c;除了用于進程外&…

開源當自強:我們不是“便宜貨”

之前人們爭相使用開源軟件&#xff0c;無非是因為它便宜、好用、易得&#xff0c;不過根據最新的開源軟件調查顯示&#xff0c;人們使用開源軟件最主要的原因還是看重它的高質量。 成本低是很過公司參與開源項目的最主要原因之一&#xff0c;而現在他們視開源是一條通往創新、省…

前端學習:Vue.js基本使用

前些天發現了一個巨牛的人工智能學習網站&#xff0c;通俗易懂&#xff0c;風趣幽默&#xff0c;忍不住分享一下給大家。點擊跳轉到教程。 Vue教程文檔&#xff1a; https://cn.vuejs.org/v2/guide/ 定義 實例&#xff1a; new Vue() 掛載點: el 數據&#xff1a;data 模…