10个 Linux/Unix下 Bash 和 KSH shell 的作业控制实例

Linux 和 Unix 属于多任务的操作系统,也就是说一个系统在同一时间段内能运行多重任务(进程)。在这个新的博客系列,我将会列出相关的 Linux 和 Unix 作业(job)控制的命令,你可以通过这些命令在 Bash 或 Korn 还有 POSIX shell 下实现执行多重任务。

什么是作业控制?

作业控制不只是能够停止/挂起(stop/suspend)正在执行的进程(命令),也可以继续/唤醒(continue/resume)执行你需要的每一个进程。这完全可以用你的操作系统和 bash/ksh 之类的 shell 或 POSIX shell 完成。

谁给作业控制的提供了环境?

Bash / Korn shell,或者是 POSIX shell 提供给了作业控制的环境。

跟作业表打个招呼吧

你的 shell 会留有一张当前作业的表单,称为作业表。当你键入命令时,shell 会给它分配一个 jobID(也称作 JOBSPEC)。一个 jobID 或 JOBSPEC只是很小的整数数值。

#1: 创建你的首个 Linux/Unix 作业

我要运行一个名为 xeyes 的命令,它会在屏幕上显示两个椭圆的眼睛,输入: $ xeyes &

输出样例:

Fig.01: 在后台运行 xeyes 命令

Fig.01: 在后台运行 xeyes 命令

我使用&符号让一个 job 在后台运行。shell 会打印一行信息类似如下:

 
  1. [1] 6891

在这个例子中,有两个数字输出,分别表示:

  • 1 : 在后台执行的 xeyes 任务的作业号为 1。
  • 6891 : 作业1的进程ID。

我在多执行一些 job:

 
  1. ## 启动一个文本编辑器,X 的系统负载显示,和 sleep 命令 ##
  2. gedit /tmp/hello.c &
  3. xload &
  4. sleep 100000 &

#2: 列出当前的作业

要查看当前 shell 的激活的任务状态,输入:

 
  1. $ jobs
  2. $ jobs -l

输出如下:

 
  1. [1] 9379 Running xeyes &
  2. [2] 9380 Running gedit /tmp/hello.c &
  3. [3]- 9420 Running xload &
  4. [4]+ 9421 Running sleep 100000 &

简要描述如下:

字段描述示例
1[1] jobID 或 JOB_SPEC - 工作号要与fg, bg, wait, kill和其他shell命令一起使用。你必须在工作号前缀添加一个百分号:(%)。
加号 (+) 标识着默认的或是现在的作业。
减号 (-) 标识着前一个作业。
%1
fg %1
kill %2
29379 进程 ID - 系统自动为每个进程创建并分配地独有的身份标志号。kill 9379
3Running 状态 - 关于作业的状态:
Running - 该 作业正在运行,还没有被外部信号挂起。
Stopped - 该作业已经被挂起。
N/A
4xeyes & command - 由shell给出的命令。script &
firefox url&

你也可以用 ps 命名列出当前系统正在运行的进程:

 
  1. $ ps

#3: 停止或挂起正在运行的作业

按下[Ctrl]-[Z]键或使用kill 命令,如下所示:

 
  1. kill -s stop PID

举个例子,启动ping 命令,然后用 Ctrl-Z 键来停止 ping 命令作业:

Animated gif 01: 挂起 ping 命令作业

Animated gif 01: 挂起 ping 命令作业

#4: 在前台恢复 挂起的/停止的作业

让我们恢复处于停止状态下的作业,让它回到前台继续运行,要将其变成当前作业,必须借助fg 命令。具体语法如下:

 
  1. ## ping 命令的作业号的值为5 ##
  2. fg %5

我也可以规定命令行开端符合字符串"ping"的作业[译注:不能出现不明确的字符串,例如如果后台有两个 vim 进程而你敲入 fg %vim 会报错。]:

 
  1. ## %String ##
  2. fg %ping

输出样例:

 
  1. 64 bytes from www.cyberciti.biz (75.126.153.206): icmp_req=3 ttl=53 time=265 ms
  2. 64 bytes from www.cyberciti.biz (75.126.153.206): icmp_req=4 ttl=53 time=249 ms
  3. 64 bytes from www.cyberciti.biz (75.126.153.206): icmp_req=5 ttl=53 time=267 ms
  4. ^C

#5: 在后台恢复 挂起/停止状态的作业

在这个例子中,我使用yum 命令更新所有安装在 Redhat 或 CentOS Linux 生产服务器上的软件包并置于后台作业。

 
  1. # yum -y update &>/root/patch.log &

然而,由于一些原因(例如,过载问题)我决定停止这个作业20分钟:

 
  1. # kill -s stop %yum

输出样例:

 
  1. [7]+ Stopped yum -y update &>/root/patch.log &

用 bg 重启停止在后台的 yum 进程

现在,我将要恢复停止的 yum -y update &>/root/patch.log & 作业,键入:

 
  1. # bg %7

或者:

 
  1. # bg %yum

输出样例:

 
  1. [7]+ yum -y update &>/root/patch.log &

#6: 杀死作业/进程

杀死yum 命令进程,输入如下kill 命令及其作业号 7:

 
  1. # kill %7

或者

 
  1. # kill 进程ID

输出样例:

 
  1. [7]+ Terminated yum -y update &>/root/patch.log &

在 Linux/FreeBSD/OS X Unix 下你也可以使用 killall 命令通过名字杀死进程或是 jobID 而不是通过 PID 

#7 为什么当我登出后 shell 会清除我的所有后台作业

在这个例子中,我将会启动 pdfwriter.py 来批量生成这个站点的 pdf 文件:

 
  1. ~/scripts/www/pdfwriter.py --profile=faq --type=clean --header=logo\
  2. --footer-left "nixCraft is GIT UL++++ W+++ C++++ M+ e+++ d-" \
  3. --footer-right "Page [of] of [total]" &

一旦当我登出shell时,pdfwriter.py 作业就会被我的 shell 杀死。为了克服这个问题需要使用shell的内置命令 disown 来告诉 shell 不要发送 HUP 信号,键入:

 
  1. $ ~/scripts/www/pdfwriter.py --profile=faq .... &
  2. $ disown
  3. $ exit

#8 使用一个名为 nohup 的外部命令阻止在登出时杀死作业

你也可以使用nohup 命令在你退出 shell 后执行作业:

 
  1. $ nohup ~/scripts/www/pdfwriter.py --profile=faq .... &
  2. $ exit

#9: 查找最后的作业的 PID

为了查找最近在后台执行的(异步)命令的进程ID,可使用 bash shell 的特殊参数 $!

 
  1. $ gedit foo.txt &
  2. $ echo "最近在后台执行的job 的PID - $!"

输出样例:

 
  1. 最近在后台执行的job PID - 9421

#10: 等候作业完成

wait 命令会等候给予的进程ID 或 作业ID指定的进程,然后报告它的终止状态。语法如下:

 
  1. /path/to/large-job/command/foo &
  2. wait $!
  3. /path/to/next/job/that-is-dependents/on-foo-command/bar

这是我的一个工作脚本:

 
  1. #!/bin/bash
  2. # A shell script wrapper to create pdf files for our blog/faq section
  3. ########################################################################
  4. # init() - Must be run first
  5. # Purpose - Create index file in $_tmp for all our wordpress databases
  6. ########################################################################
  7. init(){
  8. _php="/usr/bin/php"
  9. _phpargs="-d apc.enabled=0"
  10. _base="~/scripts"
  11. _tmp="$_base/tmp"
  12. _what="$1"
  13. for i in $_what
  14. do
  15. [[ ! -d "$_tmp/$i" ]] && /bin/mkdir "$_tmp/$i"
  16. $_php $_phpargs -f "$_base/php/rawsqlmaster${i}.php" > "$_tmp/$i/output.txt"
  17. done
  18. }
  19.  
  20. #####################################################
  21. # Without index file, we can out generate pdf files
  22. #####################################################
  23. init blog
  24.  
  25. ###########################################################
  26. # Do not run the rest of the script until init() finished
  27. ###########################################################
  28. wait $!
  29.  
  30. ## Alright, create pdf files
  31. ~/scripts/www/pdfwriter.py --profile=blog --type=clean --header=logo\
  32. --footer-left "nixCraft is GIT UL++++ W+++ C++++ M+ e+++ d-" \
  33. --footer-right "Page [of] of [total]"

Linux 和 Unix 作业控制命令总结列表

命令描述示例
&将作业置入后台命令 &
%n设置作业号为 n (数字)的作业命令 %1
%Word引用命令行开端包含 Word 的作业命令 %yum
%?Word引用命令行包含 Word 的作业命令 %?ping
%%
%+
引用当前作业kill %%
kill %+
%-引用先前作业bg %-
CTRL-Z
kill -s stop jobID
挂起或停止作业kill -s stop %ping
jobs
jobs -l
列出活动的作业jobs -l
bg将 作业置入后台bg %1
bg %ping
fg将作业置入前台fg %2
fg %apt-get

关于 shell 内置命令和外部命令的小注

运行下面的 type 命令找出给予命令是否属于内部或外部的。

 
  1. type -a fg bg jobs disown

输出样式:

 
  1. fg is a shell builtin
  2. fg is /usr/bin/fg
  3. bg is a shell builtin
  4. bg is /usr/bin/bg
  5. jobs is a shell builtin
  6. jobs is /usr/bin/jobs
  7. disown is a shell builtin

在几乎所有情况下,你都需要使用 shell 的内置命令。所有外部命令例如 /usr/bin/fg 或 /usr/bin/jobs 工作在一个不同的 shell 环境下,而不能用在父 shell 的环境下。

总结

我希望你能喜欢这篇博文系列(rss 订阅),我建议你阅读下面的更多信息:

  • 在我们的 faq 章节查阅有关进程管理的文章disoen 命令示例,jobs 命令示例,bg 命令示例,和fg 命令示例。
  • Man pages bash(1), ksh(1), ps(1), kill(1)
  • Korn shell (ksh93) 文档.
  • NU bash shell 文档.

原文发布时间为:2014-03-13

本文来自云栖社区合作伙伴“Linux中国”

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/395900.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

微信小程序 - 骨架屏

骨架屏 - “与其等待网络加载,不如提前给点暗示” 注:不适用复杂交互效果 演示 示例解释以及使用全在index.wxml中,观看需了解组件使用. 示例下载:微信小程序-骨架屏演示 转载于:https://www.cnblogs.com/cisum/p/10032448.html

图解机器学习 github_使用Github和Cloudflare建立网站的图解指南

图解机器学习 githubby Karan Thakkar由Karan Thakkar 使用GitHub和Cloudflare建立网站的插图指南 (An illustrated guide to setting up your website using GitHub and Cloudflare) You should read this if…如果...,您应该阅读此内容 You want to setup custo…

ajax拼接显示不同样式,Ajax重点整理

Ajax工作流程Ajax:在不刷新页面的情况下向服务器请求数据1.创建XMLHttpRequest对象(俗称小黄人)var xhr new XMLHttpRequest();XMLHttpRequest : http请求对象,负责实现ajax技术2.设置请求xhr.open(get, url);url:服务器地址3.发送请求xhr.send();4.注册…

java与mysql的交互_java与数据库交互常用到的一些方法

下面我整理了一下java中常用的几个与数据库交互的常用方法,仅供参考:1.执行SQL(dao层的实现类中)(1)SQL查询://import org.hibernate.Query;//import org.hibernate.Session;/*** 通过名称查找id*parampsname*returnid*/OverridepublicString…

xbmc电脑版本和手机版本学习教程

XBMC改名为Kodi了,IOS系统,Cydia源地址也同样发生了变化,新的源是:http://mirrors.kodi.tv/apt/ios/先了解一下几点知识: 教程中的各项操作,默认起始点都是“主界面”或“各分类菜单(视频、音乐…

线程管理(七)守护线程的创建和运行

声明:本文是《 Java 7 Concurrency Cookbook 》的第一章, 作者: Javier Fernndez Gonzlez 译者:郑玉婷 校对:方腾飞 守护线程的创建和运行 Java有一种特别的线程叫做守护线程。这种线程的优先级非常低,通常…

vue2中的keep-alive使用总结及注意事项

问题总结;最近在写vue移动端的项目的时候,当我切换菜单,再切换换回去的时候,发现页面出现闪动的效果,其原因是因为切换回去之后,页面重新渲染了;为了解决这一问题:查阅资料,只需要在 入口文件 App.vue 的router-view外层包裹一个keep-active标签,表示该组件被保存在内存中,不需…

grove 套件_如何通过使用Andy Grove的High Leverage Activities加快发展?

grove 套件by Guido Schmitz由Guido Schmitz 如何通过使用Andy Grove的High Leverage Activities加快发展? (How to speed up your development by using Andy Grove’s High Leverage Activities ?) Youre constantly building on new features, fixing new bugs…

ajax php 观察者模式,JavaScript观察者模式定义和dom事件实例详解

观察者模式(发布-订阅模式):其定义对象间一种一对多的依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都将得到通知。在JavaScript中,一般使用事件模型来替代传统的观察者模式。好处:(1)可广泛应用于异步编程…

python中代码段的标志是什么车_请问这段Python代码是什么意思?

ord(p) - ord(a)这个意思是以 a 为序号0,计算字符p的序号。在ASCII字符集中,小写字母a-z是连续排列的,因此如果a是0的话,那么b就是1,c就是2……以此类推。ord(p) - ord(a) 3前面一段我们解释过了,那么这一…

servlet和jsp页面过滤器Filter的作用及配置

刚刚有个朋友问我,Servlet的过滤器有什么作用? 现在发个帖子说明一下, 过滤器是一个对象,可以传输请求或修改响应。它可以在请求到达Servlet/JSP之前对其进行预处理,而且能够在响应离开Servlet /JSP之后对其…

tar命令速查

tar -c: 建立压缩档案-x:解压-t:查看内容-r:向压缩归档文件末尾追加文件-u:更新原压缩包中的文件 这五个是独立的命令,压缩解压都要用到其中一个,可以和别的命令连用但只能用其中一个。下面的参数是根据需要…

附005.Docker Compose文件详解

一 Docker Compose文件简介 compose文件使用yml格式,主要分为了四个区域:version:用于指定当前docker-compose.yml语法遵循哪个版本services:服务,在它下面可以定义应用需要的一些服务,每个服务都有自己的名…

如何使用TensorFlow构建简单的图像识别系统(第2部分)

by Wolfgang Beyer沃尔夫冈拜尔(Wolfgang Beyer) 如何使用TensorFlow构建简单的图像识别系统(第2部分) (How to Build a Simple Image Recognition System with TensorFlow (Part 2)) This is the second part of my introduction to building an image recognition system wi…

网站 服务器 用sqlite,sqlite服务器数据库

sqlite服务器数据库 内容精选换一换简要介绍SQLite是一款轻量级的关系型数据库,它的运算速度非常快,占用资源很少,不仅支持标准的SQL语法,还遵循了数据库的ACID事务。编写语言:C一句话概述:轻量级的关系型数…

type-c接口图片_TypeC接口除了充电还能干吗?这些功能都不知道,简直是在浪费...

Type C手机接口相信每个使用智能手机的朋友都很熟悉,目前已经广泛使用在智能手机领域,并且得到用户一致好评。但是对于Type C接口真正的用处很少有人知道,大部分用户只了解正反面都可充电,其他方面一概不知,对于这一点…

Zookeeper的api的简单使用(转载)

转载自: http://www.cnblogs.com/sunddenly/p/4031881.html 1.API 2.API 示例 ZooKeeper中的组成员关系 理解ZooKeeper的一种方法就是将其看作一个具有高可用性的文件系统。但这个文件系统中没有文件和目录,而是统一使用“节点”(node)的概念,称为znode…

必须使用301重定向的运用场景

必须使用301重定向的运用场景

1.1好素数

题目 题意:一个好素数的定义是,他是一个素数,然后他的左右两边10区间内存在素数,那么他就是好素数,现在让你输入一个数字,这个数字以内的好素数的数量。 解题方法:先把每一个数字是不是素数判断…

jquery.vue.js_一个Vue.js简介,面向只了解jQuery的人

jquery.vue.jsby Matt Rothenberg马特罗森伯格(Matt Rothenberg) 一个Vue.js简介,面向只了解jQuery的人 (A Vue.js introduction for people who know just enough jQuery to get by) I’ve had a love-hate relationship with JavaScript for years.我与JavaScrip…