contents




系统启动的 shell 程序取决于个人的用户 ID 配置,在 /etc/passwd 文件中,在用户 ID 记录的第 7 个字段中列出了默认的 shell 程序。

shell 的父子关系

在 CLI 提示符后输入 /bin/bash 命令或其他等效的 bash 命令时,会创建一个新的 shell 程序,这个 shell 程序被称为子 shell。

bash 命令行参数:

参数

描述

-c string

从 string 中读取命令并进行处理

-i

启动一个能够接受用户输入的交互 shell

-l

以登录的形式启动

-r

启动一个受限 shell,用户会被限制在默认目录中

-s

从标准输入中读取命令

进程列表

命令列表要想成为进程列表,这些命令就必须包含在括号里。
进程就是正在运行的程序,bash shell 是一个程序,当它运行的时候,就成为了一个进程,一个运行着的 shell 就是某种进程而已。

(pwd; ls; cd /etc; pwd; cd;)

括号的加入使得命令列表变成了进程列表,生成了一个子 shell 来执行对应的命令

另一种命令分组是将命令放入花括号中,这样做并不会创建子 shell。

{pwd; ls; cd /etc; pwd; cd;} # 命令列表

要想知道是否生成了子 shell,使用如下命令,若该命令返回 0,就表明没有子 shell。

echo $BASH_SUBSHELL
(pwd; ls; cd /etc; pwd; cd; echo $BASH_SUBSHELL) # 进程列表
(pwd; (echo $BASH_SUBSHELL)) # 嵌套进程列表

子 shell 用法

后台模式

在后台模式中运行命令可以在处理命令的同时让出 CLI。

sleep 3000& # 将会话暂停 3000 秒,并放入后台

把进程放入后台

要想将命令置入后台,可以在命令末尾加上字符 &。

tar -zcf etc.tar.gz /etc &
# 后台仍在运行
top
# 在 top 命令执行的过程中,按下 Ctrl + Z 快捷键,放入后台后暂停。
# Ctrl + C 终止

当后台作业完成之后,会在 shell CLI 提示符返回之前,显示两条信息:

[后台作业号] 后台作业进程的 ID

后台作业的结束状态未必会一直等待到合适的时候才现身。

查看后台的工作

​1​

jobs [-l]

选项

说明

-l

显示工作 PID

将后台暂停的工作恢复到前台执行

fg %工作号

选项

说明

%工作号

%号可以省略,但是要注意工作号和PID的区别

把后台暂停的工作恢复到后台执行

​2​

bg %工作号

将进程列表置入后台

(pwd; ls; cd /etc; pwd; cd; echo $BASH_SUBSHELL)&

你既可以在子shell中进行繁重的处理工作,同时也不会让子shell的I/O受制于终端。

(tar -cf Rich.tar /home/rich ; tar -cf My.tar /home/christine)&

协程

协程可以同时做两件事。它在后台生成一个子shell,并在这个子shell中执行命令。

coproc sleep 10

使用扩展语法改名:

coproc My_Job { sleep 10; }

只有在拥有多个协程的时候才需要对协程进行命名,否则的话,让 coproc 命令将其设置成默认的名字就行了。

理解 shell 的内建命令

外部命令

外部命令也称为文件系统命令,是存在于 bash shell 之外的程序。它们并不是 shell 程序的一部分。外部命令通常位于 /bin、/usr/bin、/sbin、/usr/sbin 中
当外部命令执行时,会创建出一个子进程,这种操作称为衍生。
作为外部命令 ​​​ps​​ 执行时会创建出一个子进程。

内建命令

内建命令和外部命令的区别在于前者不需要子进程来执行。它们已经和shell编译成了一体,作为 shell 工具的组成部分存在,不需要借助外部程序文件运行。
可以利用 type 命令来了解某个命令是否是内建的。
有些命令也有多种实现,例如 echo 和 pwd 既有内建命令也有外部命令。要查看命令的不同实现,使用 type 命令的 -a 选项。
which 命令只显示外部命令。

对于有多种实现的命令,如果想使用其外部命令实现,直接指明对应的文件就可以了。例如,要使用外部命令 pwd,可以输入 /bin/pwd。

使用 history 命令

history [选项][历史命令保存文件]

选项

说明

-c

清空历史命令

-w/-a

把缓存中的历史命令写入历史命令保存文件 (默认保存在家目录下 ~/.bash_history)

历史命令默认保存 1000 条,/etc/profile 中 HISTSIZE 改数值。

历史命令的调用

  • 使用上、下箭头调用以前的历史命令
  • 使用!n重复执行第 n 条命令
  • 使用!!重复执行上一条命令
  • 使用!字符串重复执行最后一条以该字串开头的命令

​history -a​​​:将命令历史记录强制写入 .bash_history 文件。
​​​history -n​​:强制重新读取 .bash_history 文件,更新终端会话的历史记录。

命令别名

alias 是另一个 shell 的内建命令。

alias -p  # 查看当前可用的别命
alias = li='ls -li'  # 创建属于自己的别名。
alias 别名='原命令'  # 设定命令别名
alias # 查询命令别名

让别名永久生效

家目录下/.bashrc

删除别名

unalias 别名

在定义好别名之后,你随时可以在 shell 中使用它,就算在 shell 脚本中也没有问题,要注意,因为命令别命属于内部命令,一个别名仅在它所被定义的 shell 进程中才有效

命令执行顺序

1 第一顺位执行用绝对路径或相对路径执行的命令
2 第二顺位执行别名
3 第三顺位执行 Bash 的内部命令
4 第四顺位执行按照 $PATH 环境变量定义的目录查找顺序找到的第一个命令


  1. “+” 号代表最近一个放入后台的工作,也是工作恢复时,默认恢复的工作。 “-” 号代表倒数第二个放入后台的工作。​​↩︎​
  2. 后台恢复执行的命令,是不能和前台有交互的,否则不能恢复到后台执行​​↩︎​