c语言多进程编程,C语言中的多进程
8种机械键盘轴体对比
本人程序员,要买一个写代码的键盘,请问红轴和茶轴怎么选?
序言
为了充分利用计算机中的多核CPU,计算机提供了两个接口使用多核CPU,两个接口分别是:多进程、多线程。本编文章将介绍多进程编程,利用多核CPU。
多进程核的个数与可同时运行的进程数相同。相反,若进程数超过核数,进程将分时使用CPU资源。但因为CPU运行速度极快,我们会感到所有进程同时运行。当然多核越多,这种感觉也明显。
fork函数创建多进程1
2
3pid_t fork(void);
fork函数将创建调用的进程副本。两个进程都将执行fork调用后的语句,子进程将复制父进程相同的内存空间,之后的程序流要根据fork函数的返回值加以区分。父进程:fork函数返回子进程ID
子进程:fork函数返回0
eg.1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22#include
int gval = 10;
int (){
pid_t pid;
int lval = 20;
gval++, lval += 5;
pid = fork();
if (pid == 0) {
gval += 2, lval += 2;
} else {//parent pro
gval -= 2, lval -= 2;
}
if (pid == 0) {
printf("Child Proc: [%d, %d] n", gval, lval);
} else {
printf("Parent Proc: [%d, %d] n", gval, lval);
}
}
运行结果:
进程与僵尸进程
僵尸进程的产生
文件操作中,关闭文件和打开文件同等重要。同样进程的创建和进程的销毁同等重要。如果未认真对待进程销毁,它们将变成僵尸进程困扰各位。
进程完成工作后(执行完main函数中的程序后)应当销毁,但有时这些进程将变成僵尸进程,占用系统中的重要资源。
子进程的终止方式:传递参数并调用exit函数
main函数中执行return语句并返回值
向exit函数传递的参数值和main函数的return语句返回的值都会传递给操作系统。而操作系统并不会销毁子进程,直到把这些值传递给产生该子进程的父进程。
eg.1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17#include
int (){
pid_t pid = fork();
if (pid == 0) { Child Pro
printf("Hi, I am a child process n");
} else {
printf("Child Process ID: %d n", pid);
}
if (pid) {
puts("End child process n");
} else {
printf("End parent process n");
}
}
销毁僵尸进程
为了销毁子进程,父进程应主动请求获取子进程的返回值。
使用wait函数1
2
3
4#include
pid wait(int * statloc);
//成功时返回终止的子进程的ID,失败时返回-1
调用此函数时如果已有子进程终止,那么子进程终止时传递的返回值(exit函数的参数值、main函数的return返回值)将保存到该函数的参数所指内存空间。WIFEXITED子进程正常终止时返回”真“ true
WEXITSTATUS返回子进程的返回值
eg.1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27#include
#in
int (){
int status;
pid_t pid = fork();
if (pid == 0) {
return 3;
} else {
printf("Child PID:%d n", pid);
pid = fork();
if (pid == 0) {
exit(7);
} else {
wait(&status);
if (WIFEXITED(status)) {
printf("Child send one: %d n", WEXITSTATUS(status));
}
wait(&status)
if (WIFEXITED(status)) {
printf("Child send tow: %d n", WEXITSTATUS(status));
}
sleep(30);
}
}
}
运行结果:
调用wait函数时,如果没有已终止的子进程,那么程序将阻塞(Blocking)直到有子进程终止。
使用waitpid函数
wait函数会引起程序阻塞,而waitpid即使没有终止的子进程也不会进入阻塞状态,而是返回0并退出。1
2
3
4
5
6
7
8
9#include
pid_t waitpid(pid_t pid, int * statloc, int options);
//成功时返回终止的子进程ID(或0),失败时返回-1
//1. pid 等待终止的目标子进程的ID, 若传递-1,则与wait函数相同,可以等待任意子进程终止
//2. ...
//3. 传递头文件sys/wait.h中声明的常量WNOHANG,即使没有终止的子进程也不会进入阻塞状态,而是返回0并退出
调用waitpid时程序不会阻塞。
eg.1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21#include
#include
int (){
int status;
pid_t pid = fork();
if (pid == 0) {
return 24;
} else {
while (!waitpid(-1, &status, WNOHANG)) {
sleep(3);
printf("sleep 3sec n");
}
if (WIFEXITED(status)) {
printf("Child send %d n", WEXITSTATUS(status));
}
}
return 0;
}
运行结果:
信号处理
signal函数
信号注册函数1
2
3
4
5
6
7#include
void (*signal(int signo, void (*func)(int)))(int);
//函数名: signal
//参数:int signo, void (*func)(int)
//返回类型:参数为int类型,返回void型函数指针
发生第一个参数代表的情况时,调用第二个参数所指向的函数。
signal函数中注册的部分特殊情况和对应的常数。SIGALRM: 已通过调用alarm函数注册的时间
SIGINT: 输入CTRL+C
SIGCHLD: 子进程终止
注册好信号后,发生注册信号时(注册的情况发生时),操作系统将调用该信号对应的函数。1
2#include
unsigned int alarm(unsigned int seconds);
如果调用该函数的同时向它传递一个正整型参数,相应时间后(以秒为单位)将产生SIGALRM信号。若向该函数传递0,则之前对SIGALRM信号的预约将取消。
eg.1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28#include
#include
#include
void timeout(int sig){
if (sig == SIGALRM) {
puts("Time out!");
}
alarm(2);
};
void keycontrol(int sig){
if (sig == SIGINT) {
puts("CTRL+C");
}
}
int (){
int i;
signal(SIGALRM, timeout);
signal(SIGINT, keycontrol);
alarm(2);
for (int i = 0; i < 3; i++) {
puts("waiting ...");
}
return 0;
}
运行结果:
发生信号时将唤醒由于调用sleep函数而进入阻塞状态的进程
sigaction函数进行信号处理1
2
3#include
int sigaction (int signo, const struct sigaction *act, struct sigaction *oldact);
c语言多进程编程,C语言中的多进程相关推荐
- LINUX 多进程编程 C语言实例
LINUX多进程编程 简单实例 1.ps与top命令 查看进程状态 2.系统调用ping,并执行 #include <stdio.h> #include <string.h> ...
- c语言soket编程,C语言socket编程使用方法
C语言socket编程使用方法 C语言是一门通用计算机编程语言,应用广泛.C语言的设计目标是提供一种能以简易的方式编译.处理低级存储器.产生少量的机器码以及不需要任何运行环境支持便能运行的编程语言.以 ...
- c语言odbc编程,c语言之odbc编程指南c语言之odbc编程指南.doc
c语言之odbc编程指南c语言之odbc编程指南 ?摘要本文在介绍了ODBC(开放性数据库连接,Open? DataBase? Connectivity)运行机制的基础上,着重讨论了VisualC++ ...
- 钻星图的c语言的编程,C 语言Socket编程教程 pdf
南漳谬悠情节层析德雅青豆丹佛脉理密封.夺理秋月弹流清切壳菜夺得沙梨.临朐硕壮着迷僚婿母权欣欣气急波器,倒把迟迟供肥东辽电学片盘挂钟劈胸麦片!龙乡足板比美性病内屏:涣然树立马具闹哄啪唧每场水力儒艮: 励 ...
- c语言winpcap编程,c语言Winpcap编程结构并接收解析arp包
c语言Winpcap编程构造并接收解析arp包 /* 程序功能: 1.构造arp包,并发送.程序参数顺序:源IP.目的IP.mac地址.flag 2.获取网络中的ARP数据包,解析数据包的内容.程序参 ...
- java语言数据库编程_JAVA语言数据库编程实例详解
本文主要向大家介绍了JAVA语言数据库编程实例详解,通过具体的内容向大家展示,希望对大家学习JAVA语言有所帮助. DOS命令登录MySQL数据库:mysql -h 127.0.0.1 -u root ...
- c语言运算符编程,C语言运算符
一.C语言的运算符 C语言有六种运算符,如下: 1)算术运算符: 2)赋值运算符: 3)sizeof运算符: 4)关系运算符: 5)逻辑运算符: 6)位运算符. 本章将只介绍算术运算符.赋值运算符和s ...
- python多进程编程实例_[python] Python多进程编程技术实例分析
这篇文章主要介绍了Python多进程编程技术,包括了线程.队列.同步等概念及相关的技巧总结,需要的朋友可以参考下 本文以实例形式分析了Python多进程编程技术,有助于进一步Python程序设计技巧. ...
- Linux基础——“C语言高级编程” C语言中的细节你真的知道吗?
文章目录 GCC简介 一.GCC编译的过程 1. 预处理: 2.编译: 3.汇编处理 4. 链接 二.GDB调试工具 1. 调试器--GDB调试流程 2. GDB的使用切记点: 3. 条件编译 三.结 ...
最新文章
- (2)iOS用UICollectionView实现Gallery效果
- 【模型开发】构建风控评分卡模型介绍(WOE/KS/ROC)
- 关于Juniper ScreenOS MIP/VIP地址说明
- eclipse 注释星号没对齐_36 个奇葩代码注释,看完笑哭了!
- 检验是否服从同一分布
- 授予数据库账号dba权限_数据库用户和权限
- pytorch自动求梯度—详解
- paip.项目文件同步-分支和合并总结V2012.9.23
- Redis学习笔记三:多机数据库的实现
- ET Reporter
- C#中使用listview的checkBoxs全选和取消全选
- 解决charles代理手机请求后,手机无法上网问题
- YTU OJ 2476 C++习题 继承与组合
- 机动车污染排放检验信息系统信息化建设目标及规范
- html5橡皮擦,用HTML5 Canvas API中的clearRect()方法实现橡皮擦功能
- 中柏pad7安装linux,中柏电脑下载与安装win7iso镜像系统教程
- IBM Spectrum LSF RTM
- Avoid passing null as the view root (needed to resolve layout parameters on the inflated layout's ro
- USB TypeC接口和USB PD快充协议,有何区别?
- java设计九宫格拼图软件哪个好用_抖音超火的朋友圈九宫格用什么软件做的? 抖音九宫格图片制作教程...