关于进程的一点理解

一、什么是进程?

进程包含存储在文件中的一组指令,该文件被读入内存并执行。正在执行的每个唯一的实例被称为进程,并且给它唯一一个标识,成为进程ID,它由操作系统确定。比如你在电脑中同时打开两个QQ,那么这两个程序就叫做进程,而且有两个不同的ID号。

二、进程如何创建?

被称为子进程的新进程由父进程的已存在的进程通过调用fork函数创建。

pid=fork();//fork函数回传给pid的值是新进程的ID,数据类型为pid_t,属于int型。

子进程被创建为父进程的一个副本。

fork函数在成功时给父进程和它创建的子进程都返回一个值:它把新创建的子进程的进程ID返回给父进程,给新创建的子进程返回;如果调用不成功,则进给父进程返回-1,并且不创建子进程。

注意:要使用fork函数必须包含unistd.h头文件。

三、进程如何退出?

子进程可以在它的父进程退出之前或者之后退出,但是通常倾向于在父进程退出之前先退出它所有的子进程。子进程在它的父进程退出之前,父进程可以获得子进程的退出状态,从而可以确定该子进程是否成功退出。

父进程可以通过调用定义在头文件wait.h中的wait函数获得子进程的退出状态。

wait函数返回退出的子进程的进程ID或者0(不存在子进程),在程序片段中被保存在pid中。

比如下面一段程序:

#include<wait.h>
...
pid_t pid;
int status;
...
/*Pause until a child process exits*/
pid=wait(&status);
if(pid>0)
        printf("pid %d status %d\n",pid,WEXITSTATUS(status));
//使用宏调用  WEXITSTATUS可以从变量status中提取出代码

四、怎样让进程中执行另一个程序?

如果想创建一个与父进程实现不同功能的新进程,首先需要用fork函数创建一个新进程,然后用实现预期操作的新指令替换与新进程相关的指令。这就需要用到execl函数,如果此函数调用成功,现有的进程指令被新进程的指令代替,原始指令不复存在。

一般进程从扩展名为.exe的可执行文件中读入这些指令,命令行参数可从execl函数中传入进程指令中。看下面的一段程序:

pid

#include<unistd.h>
...
pid_t pid;
...
pid=fork();
if (pid==0)
        execl("newprog.exe","newprog.exe",NULL);
printf("Parent process after if statement\n");
//如果子进程正在执行(pid==0),execl函数执行,用从可执行文件newprog.exe中获得的指令代替原有的指令,由于原有的指令不复存在,故子进程中不执行printf语句,而执行文件newprog.exe中的任何指令。
...

五、进程之间是如何通信的?
已知进程间通信的最古老形式为管道,它由两个文件描述符构成,一个为读打开,另一个为写打开。管道由pipe函数创建,因为并非所有的操作系统都支持全双工管道(能同时向两个方向发送信息的管道,半双工以此类推),全双工管道可以用两个半双工管道模拟,其中一个用作读,另一个用作写。

管道怎么用?

还是看一段程序吧:

#include<unistd.h>
...
int filedes[2];
char buffer[30];
...
if (pipe(filedes)<0)
{
    printf("Error Creating The Pipe\n");
    ...
}
...
//关闭读文件符,然后将字符串“buffer contents”写入写文件描述符。
if(close(filedes[0])<0)
    printf("Error Closing The Read File Descriptor\n");
strcpy(buffer,"Buffer Contents");
if(write(filedes[1],buffer,strlen(buffer))<0)
    printf("Error Writing To The Write File Descriptor\n");
...
//关闭写文件描述符,然后从读文件描述符中读去数据
if(close(filedes[1])<0)
    printf("Error Closing The Write File Descriptor\n");
if(read(filedes[0],buffer,sizeof(buffer))<0)
    printf("Error Reading From The Road File Descriptor\n");
....

最后举个实际应用中的一个简单的例子吧:

当你用浏览器上网的时候,打开的一个一个标签页就是一个一个的子进程,而浏览器是哥父进程,当你没有直接关闭浏览器的时候,出来选项“是否关闭所有的标签页”,你点击是的时候,其实是浏览器向每一个标签页发送了消息,直到全部关闭,而你的操作,每一个标签页是无法直接接收到的。

关于进程的一点理解,布布扣,bubuko.com

时间: 2024-08-02 06:59:46

关于进程的一点理解的相关文章

线程的一点理解

一.线程起源 线程的产生基于通过共享公共的内存空间来交换数据可提高协作进程间的通信效率这一思想.线程是程序执行流的最小单元,是进程中的一个实体,一个标准的线程由线程ID.寄存器集合和堆栈组成.是被系统独立调度和分配的基本单位.线程自己不拥有系统资源,只拥有一点儿在运行中必不可少的资源,但它可与同属一个进程的其它线程共享进程所拥有的全部资源.一个线程可以创建和撤消另一个线程,同一进程中的多个线程之间可以并发执行.由于线程之间的相互制约,致使线程在运行中呈现出间断性. 在某一时刻,进程内只有一个称为

我对直接插入排序的一点理解

今天复习排序,发现自己还是没什么长进,不过对于直接插入排序,还是有更深入的一点理解,这里留下点痕迹. 插入排序分为3类,即直接插入排序.二分排序以及希尔排序. 这里简单描述一下直接插入排序的思路.假如你现在是一名新生,早上全学院的学生去文体馆前集合,一个专业一列总队,而你去晚了,不知道自己该站哪,于是需要把自己插入到一个队列中去,这里模拟一下大脑的思路.因为你去晚了,所以你的同学都已经按照高矮顺序站好了,你从队尾开始比较,假如他比你低,ok,没他啥事了,如果他比你高,那他就得往后退,给你留下你站

Android measure和layout的一点理解

首先,推荐文章,http://blog.csdn.net/hqdoremi/article/details/9980481,http://www.docin.com/p-571954086.html 我理解measure的作用有2个:一个就是调用子view的measure函数,生成他们的高度和宽度,以便在自己的layout阶段参考:另一个是为父view提供关于自己的测量的width和height(这个宽度和高度往往和子view的测量高度和宽度有关),以便父view在layout阶段参考. lay

关于销售的一点理解

[关于销售的一点理解] 1.大多数人存在这样的偏见:销售人员和其他“中间人”很碍事,优良产品应该在生产出来后直接被神奇地分销出去. 这句话反着说,就正确了:销售人员和其他“中间人”很重要,优良产品应该在生产出来后由销售人员分销出去. 2.工程师喜欢制造东西,而不喜欢销售这些东西.但顾客并不会因为你生产了就来买.让顾客来买,并不像看起来那么简单. 3.广告之所以重要,是因为它确实有效.拒绝明显的推销术并不难,但广告不会立刻让你购买产品,而是为以后的购买埋下伏笔. 4.销售人员精心设计活动来改变表象

convertView&amp;setTag方法的一点理解

前言 首先我们要知道setTag方法是干什么的,SDK解释为 Tags Unlike IDs, tags are not used to identify views. Tags are essentially an extra piece of information that can be associated with a view. They are most often used as a convenience to store data related to views in th

[转载] 对函数式编程的一点理解

原文: https://github.com/nixzhu/dev-blog/blob/master/2015-07-30-functional-programming.md 对函数式编程的一点理解 虽然有不少对“函数式编程”的解释,但我没有遇到让我满意的.我不是说解释要多么的具体.全面,或者让我立马会使用.变得很厉害,我就想知道它是怎么一回事儿. 作者:@nixzhu 先考虑一个过程.假设您性别男,爱好女.有位优雅的女士愿意与您做爱,不过这位女士对做爱有些要求:前戏至少要15分钟,性交要求在3

对JS回调函数的一点理解

之前写的异步JS是纯译文,现在刚好工作了2个月,想谈谈我自己对JS回调函数的一点理解,欢迎渴望大家的指正和交流. 回调函数从形式上看就是把函数b作为参数传给函数a,在a的函数体里调用函数b 1 function a(b) { 2 b(); 3 } 4 function b() { 5 ... 6 } 这样做的意义是什么呢 1.控制执行流程,函数b只能在函数a执行后才执行 2.根据不同的需求,可以有各种各样的函数b 3.最重要的,是可以把通过函数a获取的数据传递给函数b 1 function a(

关于web开发的一点理解

对于web开发上的一点理解 1 宏观上的一点理解 网页从请求第地址 到获得页面的过程:从客户端(浏览器)通过地址 从soket把请求报文封装发往服务端   服务端通过解析报文并处理报文最后把处理的结果 封装成响应报文 发送给客户端(浏览器)  ,客户端解析响应报文  把正文(html css  javascript)渲染成我们见到的页面. 这就是我们如何看到页面的过程 图解 2对于网页的开发的框架的一点理解 上面提到了网页处理的过程  中 服务端解析请求报文 处理请求报文的过程 就是网站开发的框

对事件循环的一点理解

最近工作需要学习了解webworker-threads以应对Javascript多线程处理CPU密集型的可能性:参考文档JavaScript多线程之二 Node.js中的Web Worker; 以下是自己的一次尝试并引发的对于Javascript事件循环机制的一点理解 var Worker = require('webworker-threads').Worker; var worker = new Worker(function() { console.log(33333) postMessa