更多资料请点击:我的目录
本篇仅用于记录自己所学知识及应用,代码仍可优化,仅供参考,如果发现有错误的地方,尽管留言于我,谢谢。
多进程部分:
(1)进程的创建:
头文件 : #include <unistd.h>
函数原型: pid_t fork(void);
返回值: pid_t id = fork();
if(id > 0) //id > 0 父进程
else if(id == 0) //id == 0 子进程
else //id < 0 创建失败
调用一次fork(),返回两次,即fork()进程创建成功,会返回 id > 0 和 id == 0两个返回值。
父子进程执行顺序是不能确定的!
(2)进程的退出:
头文件: #include <unistd.h>
#include <stdlib.h>
函数原型: void _exit(int status);
void exit(int status);
参数: status为子进程退出值
子进程正常退出,status一般为0;
子进程异常退出,status一般为非0;
无返回值
exit()和_exit()的区别:
exit()结束进程的时候会刷新缓冲区,但是_exit()不会刷新缓冲区
(3)进程的回收:
头文件: #include <sys/wait.h>
函数原型 : pid_t wait(int *stat_loc);
pid_t waitpid(pid_t pid, int *stat_loc, int options);
参数: stat_loc 为子进程退出状态
pid : 小于-1: 等待进程组ID是pid里面的某个子进程
-1: 等待任意一个子进程
0: 等待调用者所在组中的任意一个子进程
大于0: 指定回收pid的子进程
option WNOHANG:非阻塞等待(即使子进程还没有结束,父进程也会直接退出)
0 :阻塞等待(即使父进程已经执行完毕,也会等待子进程结束才一起退出)
返回值: 成功 返回退出的子进程的ID号
失败 返回 -1
(4)进程ID号的获取:
头文件 : #include <sys/types.h>
#include <unistd.h>
函数原型 : pid_t getpid(void);
pid_t getppid(void);
返回值: getpid() 返回当前进程的ID号
getppid()返回当前进程的父进程的ID号
在pid_t id = fork();中,(id>0)的id值为子进程的ID号。
双进程的创建、退出、回收、进程ID号的获取应用实例:
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <error.h>
#include <sys/wait.h>
#include <sys/types.h>
int main()
{
int status; //存放子进程退出值
int ID1 = getpid(); //获取当前(父进程)ID号,能被子进程获取
printf("父进程ID1 == %d\n\n",ID1); //在进程创建前已经输出执行完毕,不会被子进程获取
int NUM = 100; //创建进程前定义,能被子进程获取
pid_t id = fork(); //创建进程
printf("创建进程成功!\n"); //创建进程后定义,能被子进程获取
if(id > 0) //父进程
{
printf("父进程中更改前NUM == %d\n",NUM); //证明父子进程的空间是相互独立的
NUM += 100; //对NUM的进行加法运算
printf("父进程中更改后NUM == %d\n",NUM); //即使是全局变量也互不干扰的
int ID2 = getpid(); //获取当前(父进程)ID号
printf("父进程ID2 == %d\n",ID2); //输出当前进程的ID号
printf("子进程id == %d\n\n",id); //输出当id>0时的ID号(就是子进程的ID号)
//wait(&status);
waitpid(id, &status, 0); //阻塞等待子进程id退出
}
else if(id == 0) //子进程
{
printf("子进程中更改前NUM == %d\n",NUM); //证明父子进程的空间是相互独立的
NUM -= 100; //对NUM的进行减法运算
printf("子进程中更改后NUM == %d\n",NUM); //即使是全局变量也互不干扰的
int ID3 = getppid(); //获取当前进程的父进程的ID号
int ID4 = getpid(); //获取当前(子进程)的ID号
printf("父进程ID1 == %d\n",ID1); //创建进程前定义的,子进程已经获取此资源
//printf("父进程ID2 == %d\n",ID2); //创建进程后定义的,子进程没有获取此资源
printf("父进程ID3 == %d\n",ID3); //输出getppid()获取的当前进程的父进程的ID号
printf("子进程ID4 == %d\n\n",ID4); //输出在子进程获取的当前ID号
exit(0); //退出子进程
}
else //创建失败
{
perror("进程创建失败!\n");
return -1;
}
return 0;
}
运行结果:
多进程的创建、退出、回收、进程ID号的获取应用实例:
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <error.h>
#include <sys/wait.h>
#include <sys/types.h>
int main()
{
int status; //存放子进程退出值
printf("(父进程)当前进程 ID == %d\n\n",getpid());
pid_t id1 = fork(); //创建进程1
printf("创建进程1成功!\n"); //创建进程1后定义,能被子进程1获取
if(id1 > 0) //父进程
{
printf("id1 > 0: 子进程1 id1== %d\n",id1);
printf("(父进程)进程1中 当前进程 ID == %d\n\n",getpid());
pid_t id2 = fork(); //创建进程2
printf("创建进程2成功!\n"); //创建进程2后定义,能被子进程2获取
if(id2 > 0) //父进程
{
printf("id2 > 0: 子进程2 id2== %d\n",id2);
printf("(父进程)进程2中 当前进程 ID == %d\n\n",getpid());
waitpid(id1, &status, 0); //阻塞等待子进程id1退出
waitpid(id2, &status, 0); //阻塞等待子进程id2退出
}
else if(id2 == 0) //子进程2
{
printf("id2 == 0:\n");
printf("(子进程2)当前进程 子进程2 ID == %d\n",getpid());
printf("(子进程2)当前进程的 父进程 ID == %d\n\n",getppid());
exit(0);
}
else //创建失败
{
perror("进程2创建失败!\n");
return -1;
}
}
else if(id1 == 0) //子进程1
{
printf("id1 == 0:\n");
printf("(子进程1)当前进程 子进程1 ID == %d\n",getpid());
printf("(子进程1)当前进程的 父进程 ID == %d\n\n",getppid());
exit(0);
}
else //创建失败
{
perror("进程1创建失败!\n");
return -1;
}
return 0;
}
运行结果: