shell脚本的三种执行方式和区别
执行方式
- 直接使用绝对,相对路径
这种是平时我们最常用的方法,例如:
./test.sh /home/thammer/test.sh
甚至PATH目录里面的,如系统自带的命令,也就是无需指定路径,直接使用命令,也是这种形式,只不过命令在bash这个解释器内部给补全了而已。
- 使用
bash
或者其他你系统带的shell解释器程序跟shell脚本,例如:
bash test.sh zsh ./test.sh
这种和第一种区别不大,稍微有区别的地方是,如果系统带有多种shell解释器,那么这里可以指定你想要的那种,否则用的就是默认的。
- 使用内置的source命令
source ./test.sh
source
命令是shell内置命令,类似的还有cd
,alias
,fg
等等。
三种方式的区别
第三种source
这种方式执行shell脚本和前两者有非常大的区别,它直接在当前shell解释器进程加载并执行命令,共享了当前解释器进程的环境变量,而前两种方式都是在当前shell解释器进程中开子进程,另起一个shell解释器,然后执行shell脚本。
如何理解?首先当我们打开一个终端,可以理解为创建并运行了一个bash程序(是否为bash和/etc/passwd的配置相关,不做分散解释),它提供的标准输入,标准输出,标准出错3个IO和用户进行交互。如果我们执行ps命令,可以看到当前bash程序的pid。
thammer@exc:~/CLionProjects/shelltest$ ps PID TTY TIME CMD 17450 pts/1 00:00:00 bash 19934 pts/1 00:00:00 ps
可以看到当前bash的pid为17450,那么我们可以在shell脚本中输出当前进程id,就知道是开启了子进程,还是直接在当前进程执行的shell脚本了。在shell中,获取当前进程id的方法是通过内置的变量$
。使用$$
(第一个是shell语法中引用变量的关键字符,第二个就是内置变量$,表示当前进程id)就获取到了当前进程pid。test.sh
如下:
#!/bin/bash echo $$
按照3种执行方式执行,结果如下:
thammer@exc:~/CLionProjects/shelltest$ ./test.sh 20129 thammer@exc:~/CLionProjects/shelltest$ bash test.sh 20132 thammer@exc:~/CLionProjects/shelltest$ source test.sh 17450
只有最后这个pid和当前bash的进程pid一样。
有何影响
由于source未开辟新的进程,所以它可以看到当前进程的环境变量,也可以修改并影响当前bash进程的环境变量,而前两种种方式不能。验证,首先在当前shell命令赋值一个变量,
VAR1=hello
通过3中方式执行如下shell脚本,test.sh
#!/bin/bash echo $VAR1 VAR1=world
执行
thammer@exc:~/CLionProjects/shelltest$ VAR1=hello thammer@exc:~/CLionProjects/shelltest$ ./test.sh thammer@exc:~/CLionProjects/shelltest$ echo $VAR1 hello thammer@exc:~/CLionProjects/shelltest$ source ./test.sh hello thammer@exc:~/CLionProjects/shelltest$ echo $VAR1 world
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· 开源Multi-agent AI智能体框架aevatar.ai,欢迎大家贡献代码
· Manus重磅发布:全球首款通用AI代理技术深度解析与实战指南
· 被坑几百块钱后,我竟然真的恢复了删除的微信聊天记录!
· AI技术革命,工作效率10个最佳AI工具