基于Linux下的多行程fork詳解
前言:
在學習C/C++的路上,想要更精進知識面和深度,多執行緒行程等知識點是一定要掌握的,是高并發服務器和TCP socket編程的必經之路,下面由博主帶來fork()函式創建多行程的詳解;
fork函式
作用: 創建子行程 原型: pid_t fork(void) 函式引數: 無 回傳值:
呼叫成功:父行程回傳子行程的PID(子行程id號),子行程回傳0
呼叫失敗:回傳-1,需要設定errno值,
父行程呼叫fork函式創建一個子行程,子行程的用戶區和父行程的用戶區完全一樣,但是內核區完全不一樣,就比如說父行程和子行程的PID就不一樣,
在linux終端下輸入 man fork 會查到fork函式的詳解

意思為創建子行程,
pid_t fork(void)
1.fork函式的回傳值?
父行程回傳是子行程的PID,這個值肯定是>0; 子行程回傳的是0; 注意:并不是一個行程回傳兩個值,而是由父子行程各自回傳一個值
2.父子行程的執行邏輯:
父行程執行pid>0的邏輯,子行程執行pid==0的邏輯;
2.父子行程誰先執行?
程式執行來看是隨機執行,但是從根上來看是誰先搶到cpu時間片誰先執行
fork代碼的示例
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<sys/types.h>
#include<unistd.h>
int main()
{
//創建子行程
pid_t pid=fork();
//創建失敗,,列印錯誤
if(pid<0)
{
perror("fork error");
return -1;
}
//父行程
else if(pid>0)
{
printf("father: pid==[%d],fpid==[%d]\n",getpid(),getfppid());
sleep(1);
}
//子行程
else if(pid==0)
{
printf("child:pid=[%d],fpid==[%d]\n",getpid(),getppid());
}
return 0;
}
運行代碼如下::::::

父行程的行程id為5147,創建的子行程為5148,5148的父行程又是5147;
而行程2433我們可以通過 終端指令下 ps -ef |grep 2433查看

回圈創建子行程注意點
我們對上面的代碼進行改造,改造成回圈三次創建子行程,代碼如下
//回圈創建n個子行程
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<sys/types.h>
#include<unistd.h>
int main()
{
int i=0;
for(i=0;i<3;i++)
{
//創建子行程
pid_t pid=fork();
if(pid<0)
{
perror("fork error");
return -1;
}
//父行程
else if(pid>0)
{
printf("father: pid==[%d],fpid=[%d]\n",getpid(),getppid());
sleep(1);
}
//子行程
else if(pid==0)
{
printf("child:pid=[%d],fpid=[%d]\n",getpid(),getppid());
}
}
}
如果這樣,,表面上是創建了三個子行程,實際上是創建了7個,原因如下
當i = 0時,父行程m創建一個子行程x1;
當i = 1時,父行程m創建一個子行程x2,同時x又創建一個子行程y1(孫子行程);
當i = 2時, 父行程m創建一個子行程x3,同時x1又創建一個子行程y2,y1也創建了子行程q1(曾孫行程),x2又創建一個子行程f2;

由圖可以直觀的看到總共創建的子行程為7個,算上父行程為8個,且每個子行程的父執行緒不一定相同,所以直接回圈創建子行程方法并不正確

若我們想要創建同為兄弟的子執行緒只需要在創建子執行緒處(當pid==0的邏輯里)添加break跳出回圈即可創建同級下的子行程如圖所示:::

如果結果為三個子行程的父行程同為5276,成功創建,,
轉載請註明出處,本文鏈接:https://www.uj5u.com/qita/287259.html
標籤:其他
上一篇:linux下CMake的簡單介紹
