1.基本概念
- sh(Bourne shell):UNIX系统上最早出现的shell,不支持job control和命令历史等功能,主要用于执行脚本。
- bash(Bourne Again Shell):由GNU开发的shell,在sh的基础上增加了很多交互功能,bash向后兼容sh。反之则不亦然。
2.SHELL执行命令过程
在交互shell的命令窗口,用户在命令行输入命令后,一般情况下shell会fork并exec该命令,但是shell的内建命令例外,执行内建命令相当于调用shell进程中的一个函数,并不创建新的进程。
用type命令查看是否为内建命令,内建命令没有单独的man手册 ,在man手册中查看内建命令:
$man bash-builtins
$type cd 查看cd是否为内建命令
内建命令也可用$?显示命令执行结果。
$ cd xxx
-bash: cd: xxx: No such file or directory
$ echo $?
1
2.1建立脚本script.sh:
#!/bin/sh
cd ..
ls
Shell脚本中用#表示注释,但如果#位于第一行开头,并且是#!(称为Shebang)则它表示该脚本使用后面指定的解释器/bin/sh解释执行。
2.2执行过程
目录结构体如下:
shell
├── test
│ └── script.sh
└── test_a
- 不需要可执行权限执行脚本
test$ /bin/sh ./script.sh
test test_a
- 添加可执行权限:
test$ chmod +x script.sh
test$ ./script.sh
test test_a
上述两种方法本质一样,执行脚本的步骤为:
- 交互shell(bash)fork并exec一个子shell(sh)用于执行脚本,bash等待sh终止。
- sh读取脚本中的cd …命令,调用相应的函数执行内建命令,置环境变量PWD为上一级目录。
- sh读取脚本中的ls命令,fork并exec这个程序,列出当前目录的文件,sh等待ls终止。
- ls终止后,sh继续执行,读到脚本末尾,sh终止。
- sh终止后,bash继续执行,打印提示符等待用户输入。
2.3 内建命令source和.执行shell
这种方式也不会创建子Shell,而是直接在交互式Shell下逐行执行脚本中的命令。脚本不需要有可执行权限。
test $. ./script.sh
test test_a
shell$
命令行执行命令
命令行下输入的命令用()括号括起来,那么也会fork出一个子Shell执行小括号中的命令,一行中多个命令用“;”隔开
test $(cd ..;ls -l) 不会改变当前目录,显示上一级目录的列表。
test test_a
test $
test $cd ..;ls -l 到上一级目录,显示上级目录的列表
test test_a
shell $