day27- 系统编程之 进程
一、补充
1.1 sprintf函数
sprintf函数打印到字符串中(要注意字符串的长度要足够容纳打印的内容,否则会出现内存溢出),而printf函数打印输出到屏幕上。sprintf函数在我们完成其他数据类型转换成字符串类型的操作中应用广泛
int sprintf( char *buffer, const char *format [, argument,…] );
除了前两个参数固定外,可选参数可以是任意个。buffer是字符数组名;format是格式化字符串(像:”%3d%6.2f%#x%o”)
- 可以控制精度
char str[20];
double f=14.309948;
sprintf(str,”%6.2f”,f);
可以将多个数值数据连接起来
char str[20];
int a=20984,b=48090;
sprintf(str,”%3d%6d”,a,b);
str[]=”20984 48090”可以将多个字符串连接成字符串
char str[20];
char s1[5]={‘A’,’B’,’C’};
char s2[5]={‘T’,’Y’,’x’};
sprintf(str,”%.3s%.3s”,s1,s2);
二、基础概念
2.1 进程
进程是一个程序执行的过程,会去分配内存资源,cpu的调度
作用:让操作系统并发执行,希望在短的时间内,多个任务同时进行
pcb:
vim -t
task_struct一个结构体,process control block print circuit board
线程号
PID,进程标识符
当前工作路径 chdir //了解
umask 0002 //了解
进程打开的文件列表 文件IO中有提到
信号相关设置 处理异步io,
用户id,组id
进程资源的上限
ulimit -a,显示资源上限。
2.2 进程与程序的区别
程序:静态
存储在硬盘中代码,数据的集合
进程:动态
程序执行的过程,包括进程的创建、调度、消亡
.c ----> a.out-----> process(pid)
1)程序是永存,进程是暂时的
2)进程有程序状态的变化,程序没有
3)进程可以并发,程序无并发
4)进程与进程会存在竞争计算机的资源
5)一个程序可以运行多次,变成多个进程
一个进程可以运行一个或多个程序
内存的分布:0-3G,是进程的空间,3G-4G是内核的空间,虚拟地址
虚拟地址 * 物理内存和虚拟内存的地址 映射表 1page=4kMAP共享库
Stack栈
heap堆
data数据
code代码段
进程分类:
1、交互式进程
2、批处理进程 shell脚本
3、 守护进程
进程的状态:
3个状态,就绪→执行态→阻塞(等待,睡眠)基本操作系统
2.3 进程的调度
man -k //模糊搜索
实时操作系统:规定时间内完成
分时操作系统:尽量在规定时间内完成(如Linux、Windows等)
后台任务
先来先服务
时间片轮转
宏观并行
微观串行
三、进程命令
1.ps aux 查看进程相关信息
|less 屏满等待
|grep 51283 51283为进程的PID,寻找该PID
pstree -p 查看进程树,显示PID
2.top 根据CPU占用率查看进程相关信息
3.kill和killall发送一个信号
kill -2 PID 15
发送信号+PID对应的进程,默认接收者关闭
-2 委婉提醒关闭
-9强制关闭
killall -9 进程名
发送信号 进程名对应的所有进程
killall a.out
四、相关函数
4.1 fork函数
pid_t fork(); 叉子
一次调用,会返回两次。
子进程先运行还是父进程先进程,顺序不确定
变量不共享:
子进程复制父进程的0到3g空间和父进程内核中的PCB,但id号不同。
功能:通过该函数可以从当前进程中克隆一个同名新进程。
克隆的进程称为子进程,原有的进程称为 父进程。
子进程是父进程的完全拷贝。
子进程的执行过程是从fork函数之后执行。子进程的id号肯定比父进程的id号大
子进程与父进程具有相同的代码逻辑。返回值:int 类型的数字。
在父进程中:成功 返回值是子进程的pid号 >0
失败 返回-1;
在子进程中:成功 返回值 0
失败 无
4.2 getpid函数
pid_t getpid(void);
功能:获得调用该函数进程的pid
参数:缺省
返回值: 进程的pid
4.3 getppid函数
pid_t getppid(void);
功能:获得调用该函数进程的父进程pid号
参数: 缺省
返回值: 返回父进程id号
五、中断
父子进程的关系:
子进程是父进程的副本。子进程获得父进程数据段,堆,栈,正文段共享。写时复制:提高运行效率;
在fork之后,一般情况那个会先运行,是不确定的。如果非要确定那个要先运行,需要IPC机制。
区别:
1)fork的返回值
2)pid不同
进程退出的8种情况:
主动退出:
1)main 中return
2)exit(), c库函数,会执行io库的清理工作,关闭所有 的流,以及所有打开的文件。已经清理函数(atexit)。
3)_exit,_Exit 会关闭所有的已经打开的文件,不执行清理函数。
4) 主线程退出
5)主线程调用pthread_exit异常终止:
6)abort()//禁止应用层调用
7)signal kill pid
8)最后一个线程被pthread_cancle线程属于进程的一部分,进程工作时,最少有一个线程
六、练习
6.1 动态生成n个子进程,并打印输出各自进程的pid号。
6.2 设计一个程序,动态生成两个进程,分别向相同的文件中 写入不同的数据,要表明是两个进程同时写入的数据。
示例:
父进程1123 186 16:02:10
子进程1124 188 16:02:15