0
点赞
收藏
分享

微信扫一扫

数组的存储和压缩

斗米 2023-06-01 阅读 44

进程指正在运行的程序,如下图示,是资源分配的最小单位,可以通过“ps ”或“top”等命令查看正 在运行的进程,线程是系统的最小调度单位,一个进程可以拥有多个线程,同一进程里的线程可以共享此 进程的同一资源

 每个进程都有一个唯一的标识符,既进程 ID,简称 pid

进程间的通信的几种方法?

进程的三种基本状态以及转换

 进程创建

创建进程常用函数如下定义:

 实验代码

在程序中,父进程中创建一个子进程。

#include <stdio.h>
#include <sys/types.h>
#include <unistd.h>

int main(int argc, char const *argv[])
{
    pid_t pid;
    int i = 1;
     
    pid = fork();
    if(pid > 0)   //父进程
    {
       printf("this is  child  pid: %d   parent pid: %d\n",getpid(),getppid()); 
       printf("parent data: %d \n",i);

    }else if (pid  == 0)  //子进程
    {   
        //sleep(1);   //先运行父进程
        printf("this is  child  pid: %d\n",getpid());
        printf("child data: %d \n",i);
      

    }else if (pid < 0)
    {
        printf("cread failed\n");
        return -1;
    }
    
  
    return 0;
}

在 Ubuntu 上编译运行,打印进程号如下图所示:

 

exec 函数

exec 函数详解如下表所示:

 以下函数都是根据 execve 实现

int execl(const char *path, const char *arg, .../* (char *) NULL */);
int execlp(const char *file, const char *arg, .../* (char *) NULL */);
int execle(const char *path, const char *arg, .../*, (char *) NULL, char * const envp[] */);
int execv(const char *path, char *const argv[]);
int execvp(const char *file, char *const argv[]);
int execvpe(const char *file, char *const argv[],char *const envp[]);

实验代码:

#include <stdio.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/wait.h>

int main(int argc, char const *argv[])
{
    pid_t pid;
    char *arr[] = {"ls","-l",NULL};
    
    /*exec族函数
    int execl(const char *path, const char *arg, ... );
    int execv(const char *path, char *const argv[]);
    */
  
    pid = fork();
    if(pid > 0)   //子进程
    {
       printf("this is  parent  pid: %d\n",getpid());
       wait(NULL);     //回收子进程

    }else if (pid  == 0)  //父进程
    {   
        //sleep(1);   //先运行子进程
        printf("this is  child  pid: %d  parent pid: %d\n",getpid(),getppid()); 
        //execl("/bin/ls","ls","-l",NULL);
        execv("/bin/ls",arr);      
        exit(-1);
        

    }else if (pid < 0)
    {
        printf("cread failed\n");
        return -1;
    }
    
  
    return 0;
}

执行结果

 

 ps 和 kill 命令

ps 命令:ps 命令可以列出系统中当前运行的那些进程。

命令格式:ps [参数]

命令功能:用来显示当前进程的状态

常用参数: aux

kill 命令:kill 命令用来杀死进程 举例:kill -9(SIGKILL) PI

进程的状态:

 

孤儿进程与僵尸进程:

孤儿进程:父进程结束以后,子进程还未结束,这个子进程就叫做孤儿进程。

僵尸进程:子进程结束以后,父进程还在运行,但是父进程不去释放进程控制块,这个子进程就叫做僵尸 进程。

实验代码 在程序中,创建的子进程变为孤儿进程:

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
int main(void)
{
    int i=0;
    pid_t pid;
    // 创建一个子进程
    pid = fork();
    if (pid < 0)
    {
        printf("fork is error \n");
        return -1;
    }
    //父进程 让父进程先结束,并打印进程 PID
    if (pid > 0)
    {
      printf("pid is %d\n", getpid());
    }
    //子进程,让子进程等待一会,让父进程先结束,并打印子进程的父进程的 pid
    if (pid == 0)
    {
        sleep(2);
        printf("parent pid is %d\n", getppid());
    }
    return 0;
}

编译运行,如下图所示:

 如上图所示,子进程中打印的父进程的进程号和父进程的进程号是不一样的,说明创建的子进程变成 了孤儿进程,此进程被系统的 init 进程"领养"了。

 实验代码 在程序中,子进程变为僵尸进程:

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
int main(void)
{
    int i=0;
    pid_t pid;
// 创建一个子进程
    pid = fork();
    if (pid < 0)
    {
        printf("fork is error \n");
        return -1;
    }
    //父进程 让父进程先结束,并打印进程 PI
    if (pid > 0)
    {
    while(1);
    }
    //子进程,让子进程先结束
    if (pid == 0)
    {
        printf("This is child\n");
        exit(0);
    }
    return 0;
}

编译运行,如下图所示:

再打开另一个终端,查看此进程如下图所示为僵尸进程。 

 

wait()函数

 与 wait 函数的参数有关的俩个宏定义:

WIFEXITED(status):如果子进程正常退出,则该宏定义为真

WEXITSTATUS(status):如果子进程正常退出,则该宏定义的值为子进程的退出值。

实验代码:

在程序中,使用 wait()函数,防止僵尸进程的产生

#include <stdio.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/wait.h>


int main(int argc, char const *argv[])
{
    pid_t pid;
    int start; 
    pid = fork();
    //让父进程先运行,没有时间去释放进程控制快
    if(pid > 0)  //父进程
    {   
         pid = wait(&start);
         if (WIFEXITED(start) == 1)   //正常退出为真
         {
           printf("return value is %d\n",WEXITSTATUS(start));
         }
         
    }
    //让子进程先结束
    else if (pid == 0)   //子进程
    {   
       sleep(2);
       printf("this is child\n");
       printf("child pid:%d\n",getpid());
       exit(0);  //对应WEXITSTATUS(start)的退出值
    }
    else if (pid < 0)
    {
       printf("cread fork faile\n");
       exit(-1);
    }
    
    
    
    return 0;
}

编译运行,如下图所示:

 

举报

相关推荐

0 条评论