关于 Shell 脚本的经典十三问

关于 Shell 脚本的经典十三问

1、为何叫做 Shell?

我们知道计算机的运作离不开硬件,但却无法直接操作硬件,硬件的驱动只能通过一种称之为“操作系统(OS,Opertating System)的软件来管控。Linux 严格来说是一个操作系统(OS)。

使用者没有办法直接操作 Kernel,而是通过 Kernel 的“外壳”程序,也就是所谓的 Shell 来与 Kernel 沟通。Shell 是一个使用者与系统的交互界面(Interface),只能通过命令行(Command line)来使用系统来完成工作。因此 Shell 最简单的定义就是:命令解译器(Command Interpreter)

将使用者的命令翻译给内核处理;

同时,将内核处理结果翻译给使用者。

不同的 OS 使用不同的 Kernel;同一个 kernel 之上,也可以使用不同的 Shell,常见的 Shell 有sh、bash、csh、ksh 等

2、Shell prompt(PS1)与 Carriage Return(CR)的关系?

成功登录一个 Shell 终端后,光标左边部分称之为提示符 Prompt,通常一般用户使用$,管理员用户使用#

Shell Prompt:可以输入命令了,键入命令后,直到读进 CR(Carriage Return)字符为止

Carriage Return:可以执行命令了

若从技术的细节来看,Shell 会依据 IFS(Internal Field Seperator)将 Command line 所输入的文字拆解为”字段”(word/field)。然后再针对特殊字符(meta)先作处理,最后重组整行command line。

3、别人echo,你也echo,试问 echo 知多少?

echo 将 argument送到标准输出(stdout),通常显示在屏幕

stdin 标准输入
stdout 标准输出
stderr 标准错误输出

echo -n  # 取消换行符echo -e  # 启用反斜杠转译

4、双引号””与单引号”有什么区别?

hard quote:''(单引号),关闭所有引用

soft quote:""(双引号),保留$引用

5、var=value? export 前后差在哪?

变量定义:name=value,等号左右两边不能使用分隔符。

变量替换:echo ${name}

export变量:export name=value,使变量成为环境变量

# 本地变量A=B# 取消变量unset A# 环境变量export A=B

6、exec 跟 source 差在哪?

环境变量只能从父进程到子进程单向传递。换句话说:在子进程中环境如何变更,均不会影响父进程的环境。
当我们执行一个shell script时,其实是先产生一个sub-shell的子进程, 然后sub-shell再去产生命令行的子进程。关注Linux中文社区

# 创建子shell执行脚本./1.sh# 当前shell执行source 1.sh# 当前shell执行后退出exec 1.sh

7、( ) 与 { } 差在哪?

( )将 command group 置于 sub-shell 执行
{ }则是在同一个shell内完成

8、$(()) 与 $() 还有 ${} 差在哪?

# 假设我们定义了一个变量为:file=/dir1/dir2/dir3/my.file.txt# 我们可以用 ${ } 分别替换获得不同的值:# 1. shell字符串的非贪婪(最小匹配)左删除${file#*/} # 拿掉第一条 / 及其左边的字符串:dir1/dir2/dir3/my.file.txt# 2. shell字符串的贪婪(最大匹配)左删除${file##*/} # 拿掉最后一条 / 及其左边的字符串:my.file.txt${file##*.} # 拿掉最后一个 . 及其左边的字符串:txt# 3. shell字符串的非贪婪(最小匹配)右删除:${file%/*} # 拿掉最后条 / 及其右边的字符串:/dir1/dir2/dir3${file%.*} # 拿掉最后一个 . 及其右边的字符串:/dir1/dir2/dir3/my.file# 4. shell字符串的贪婪(最大匹配)右删除:${file%%/*} # 拿掉第一条 / 及其右边的字符串:(空值)${file%%.*} # 拿掉第一个 . 及其右边的字符串:/dir1/dir2/dir3/my记忆的方法为:# 是去掉左边(在键盘上 # 在 $ 之左边)% 是去掉右边(在键盘上 % 在 $ 之右边)单一符号是最小匹配﹔两个符号是最大匹配。

# 5. shell字符串取子串:${file:0:5}:提取最左边的 5 个字节:/dir1${file:5:5}:提取第 5 个字节右边的连续 5 个字节:/dir2# 6. shell字符串变量值的替换:${file/dir/path}:将第一个 dir 提换为 path:/path1/dir2/dir3/my.file.txt${file//dir/path}:将全部 dir 提换为 path:/path1/path2/path3/my.file.txt# 7. ${}还可针对变量的不同状态(没设定、空值、非空值)进行赋值:${file-my.file.txt} :假如 $file 没有设定,则使用 my.file.txt 作传回值。(空值及非空值时不作处理) ${file:-my.file.txt} :假如 $file 没有设定或为空值,则使用 my.file.txt 作传回值。(非空值时不作处理)${file+my.file.txt} :假如 $file 设为空值或非空值,均使用 my.file.txt 作传回值。(没设定时不作处理)${file:+my.file.txt} :若 $file 为非空值,则使用 my.file.txt 作传回值。(没设定及空值时不作处理)${file=my.file.txt} :若 $file 没设定,则使用 my.file.txt 作传回值,同时将 $file 赋值为 my.file.txt 。(空值及非空值时不作处理)${file:=my.file.txt} :若 $file 没设定或为空值,则使用 my.file.txt 作传回值,同时将 $file 赋值为 my.file.txt 。(非空值时不作处理)${file?my.file.txt} :若 $file 没设定,则将 my.file.txt 输出至 STDERR。(空值及非空值时不作处理)${file:?my.file.txt} :若 $file 没设定或为空值,则将 my.file.txt 输出至 STDERR。(非空值时不作处理)tips:以上的理解在于, 你一定要分清楚 unset 与 null 及 non-null 这三种赋值状态.一般而言, : 与 null 有关, 若不带 : 的话, null 不受影响, 若带 : 则连 null 也受影响.

# 8. 计算shell字符串变量的长度:${#var}${#var} 可计算出变量值的长度:${#file} 可得到 27 ,因为 /dir1/dir2/dir3/my.file.txt 刚好是 27 个字节...# 9. bash数组(array)的处理方法数组:A=(a b c d)引用数组:${A[@]}${A[*]}访问数组成员${A[0]}计算数组长度${#A[@]}${#A[*]}数组重新赋值A[2]=xyz# 10.$(( ))是用来做整数运算的 a=5;b=7;c=2;echo $(( a + b * c))

9、$@ 与 $* 区别在哪?

"$@"则可得到 “p1” “p2 p3” “p4” 这三个不同的词段

"$*"则可得到 “p1 p2 p3 p4” 这一整串单一的词段

另外,搜索公众号Linux就该这样学后台回复“git书籍”,获取一份惊喜礼包。‍

10、&& 与 || 差在哪?

1、test命令有两种形式

test expression

[ expression ]

2、bash的test目前支持三种测试对象

string:字符串

integer:整数

file:文件

3、当 expression 为真是返回 0(true) ,否则返回 非0(false)

command1 && command2  command2 只有在 command1 的RV为0(True)的条件下执行。

command1 || command2  command2只有在command1的RV为非0(False)的条件下执行。

4、先替换变量再比较

A=123[ -n "$A" ] && ([ "$A" -lt 100 ] || echo "too big")unset A

11、> 与 < 差在哪?

0: Standard Input(STDIN)
1: Standard Output (STDOUT)
2: Standard Error Output(STDERR)

我们可用 < 来改变读进的数据信道(stdin),使之从指定的档案读进。

我们可用 > 来改变送出的数据信道(stdout, stderr),使之输出到指定的档案。

ls my.file no.such.file 1> file.out 2>file.err# 2>&1 就是将stderr并进stdout做输出ls my.file no.such.file 1> file.out 2>&1# /dev/null 空ls my.file no.such.file >/dev/null 2>&1cat  file# 在 IO Redirection 中,stdout 与 stderr 的管道会先准备好,才会从 stdin 读进资料。# 也就是说,在上例中,> file 会先将 file 清空,然后才读进 < file , # 但这时候档案已经被清空了,因此就变成读不进任何数据了

12、你要if还是case呢?

# ifecho -n "Do you want to continue?(Yes/No):"read YNif [ "$YN"=Y -o "$YN"=y -o "$YN"="Yes" -o "$YN"="yes" -o "$YN"="YES"];thenecho "continue"elseexit 0fi# caseecho -n "Do you want to continue?(Yes/No):"read YNcase "$YN" in[Yy]|[Yy][Ee][Ss])echo "continue";;*)exit 0esac

13、for what? while与until差在哪?

# forfor ((i=1;i<=10;i++))doecho "num is $i"done# whilenum=1while [ "$num" -le 10 ]; doecho "num is $num"num=$(($num + 1))done# untilnum=1until [ "$num" -gt 10 ]; doecho "num is $num"num=$(($nu + 1))done

break 是结束 loop

return 是结束 function

exit 是结束 script/shell

以上就是关于 Shell 脚本的经典十三问的详细内容,更多请关注创想鸟其它相关文章!

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。
如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 chuangxiangniao@163.com 举报,一经查实,本站将立刻删除。
发布者:程序猿,转转请注明出处:https://www.chuangxiangniao.com/p/108619.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
Sublime处理CSS预处理器输出文件技巧_快速编译自动刷新页面样式
上一篇 2025年11月22日 22:23:11
thinkphp5支持swoole携程吗
下一篇 2025年11月22日 22:25:13

相关推荐

  • Linux如何创建新用户并设置初始密码

    Linux如何创建新用户并设置初始密码Linux如何创建新用户并设置初始密码Linux如何创建新用户并设置初始密码Linux如何创建新用户并设置初始密码

    创建新用户并设初始密码需用useradd加passwd命令,如sudo useradd -m -s /bin/bash devuser创建用户,sudo passwd devuser设置密码;通过sudo usermod -aG sudo devuser赋予sudo权限;密码策略应包含长度、复杂度、…

    2026年9月21日 用户投稿
    000
  • LINUX怎么判断一个文件是否存在_Linux判断文件是否存在方法

    1、使用test命令或[ ]、[[ ]]结构结合-f选项可判断文件是否存在,返回0表示存在;2、通过if语句实现条件判断;3、使用-d、-L等选项可检测目录、符号链接等类型。 如果您需要在脚本或命令行中确认某个文件是否存在于系统中,可以通过多种方式检查其状态。这类操作常用于条件判断和自动化流程控制。…

    2026年9月21日
    000
  • Java中浮点数比较的陷阱:理解double类型的不精确性与正确比较方法

    java中`double`类型因其二进制浮点表示的固有不精确性,即使在相同java版本和架构下,也可能在不同环境中产生微小的数值差异。直接使用`==`比较浮点数是不可靠的,因为它无法容忍这些细微的舍入误差。正确的做法是采用基于容差(epsilon)的比较方法,通过判断两数之差的绝对值是否小于一个预设…

    2026年9月21日
    100
  • Linux目录结构与文件系统设计理念

    Linux目录结构以根目录为起点,遵循“一切皆文件”理念,通过标准化层级划分(如/bin、/etc、/home等)实现资源统一管理,结合FHS标准、灵活挂载机制与权限模型,提升系统可维护性、安全性和跨发行版兼容性,体现简洁高效的设计哲学。 Linux的目录结构与文件系统设计体现了简洁、统一和高度模块…

    2026年9月21日
    100
  • 如何避免协程中的共享资源竞争?

    避免协程中的共享资源竞争可以通过以下方法:1. 使用锁(locks),如互斥锁或读写锁,确保同一时间只有一个协程访问共享资源。2. 采用无锁数据结构(lock-free data structures),通过原子操作和cas操作提高并发性能。3. 实施消息传递(message passing),通过…

    2026年9月21日
    000
  • mysql如何配置默认存储引擎

    首先查看当前默认存储引擎,通过SHOW VARIABLES命令确认;然后编辑my.cnf或my.ini文件,在[mysqld]下添加default-storage-engine=InnoDB;接着重启MySQL服务使配置生效;最后验证更改结果并检查建表默认引擎。 MySQL 默认存储引擎的配置可以通…

    2026年9月21日
    000
  • VSCode怎么生成项目模板_VSCode使用自定义代码片段创建项目模板教程

    答案:VSCode可通过自定义代码片段高效生成文件模板,结合工作区设置与脚手架工具实现项目初始化。利用用户代码片段(User Snippets)定义常用代码结构,如React组件或HTML骨架,通过prefix触发,支持制表位快速编辑;推荐将团队共享片段设为工作区级并提交至Git,确保规范统一;配合…

    2026年9月21日
    600
  • Jedis jsonGet 方法返回字节数组值末尾出现 .0 的处理策略

    当使用jedis客户端的`jsonget`方法从redis获取json数据时,如果其中包含字节数组(如xml字符串的字节表示),可能会因底层json库(如gson或org.json)的默认行为,导致数字被统一上转型为`double`类型,从而在输出中显示`.0`后缀。本文将深入探讨此问题产生的原因,…

    2026年9月21日
    200
  • Laravel与Vue.js/React前端框架集成

    laravel可以与vue.js或react集成。1) 使用命令“php artisan preset vue”或“php artisan preset react”设置开发环境。2) 在laravel视图中引入编译后的javascript文件。3) 通过laravel的api路由和前端框架的htt…

    2026年9月21日
    000
  • mysql索引的类型和作用有哪些

    MySQL常见索引类型包括:1. 普通索引用于加速查询;2. 唯一索引确保列值唯一;3. 主键索引为唯一非空且自动创建聚簇索引;4. 聚簇索引决定数据物理存储顺序,每表仅一个;5. 非聚簇索引保存主键值,需回表查询;6. 覆盖索引避免回表提升性能;7. 联合索引遵循最左前缀原则;8. 全文索引支持文…

    2026年9月21日
    000
  • Linux怎么使用systemctl管理服务

    Linux怎么使用systemctl管理服务Linux怎么使用systemctl管理服务Linux怎么使用systemctl管理服务Linux怎么使用systemctl管理服务

    systemctl是Linux中管理systemd服务的核心工具,提供统一命令集来启动、停止、重启、查看服务状态及设置开机自启,支持并行启动、依赖管理与Cgroups资源控制,相比SysVinit更高效;通过创建/etc/systemd/system/下的.service文件可自定义服务,包含[Un…

    2026年9月21日 用户投稿
    100
  • Linux如何查看命令别名alias使用方法

    直接输入 alias 命令可列出当前会话所有别名,如需查看特定命令是否为别名可用 type 命令;别名通过简化常用命令提升效率并减少错误,临时别名在当前会话生效,永久别名需写入 ~/.bashrc 或 ~/.zshrc 文件,删除则用 unalias 命令;别名适用于简单命令替换,函数支持参数与逻辑…

    2026年9月21日
    000
  • Linux怎么监控特定进程的运行状态

    Linux怎么监控特定进程的运行状态Linux怎么监控特定进程的运行状态Linux怎么监控特定进程的运行状态Linux怎么监控特定进程的运行状态

    监控Linux进程需综合使用ps、top、htop、pgrep和systemctl等工具,结合资源占用、进程状态、日志输出和进程数量判断是否异常,并通过systemd的Restart机制或看门狗脚本实现自动重启,同时利用journalctl、sar、atop及Prometheus+Grafana等方…

    2026年9月21日 用户投稿
    000
  • mysql如何启用binlog日志

    MySQL启用binlog需修改配置文件添加log-bin和server-id,重启服务后执行SHOW VARIABLES LIKE ‘log_bin’验证是否为ON,确认启用。 MySQL启用binlog日志需要修改配置文件并重启服务,同时可进行简单验证确保生效。以下是具体…

    2026年9月21日
    000
  • Linux命令行如何查看登录用户

    Linux命令行如何查看登录用户Linux命令行如何查看登录用户Linux命令行如何查看登录用户Linux命令行如何查看登录用户

    答案是 who、w 和 users 命令用于查看Linux系统登录用户,其中 who 显示登录用户及终端信息,w 还显示用户正在执行的命令和系统负载,users 仅输出用户名列表。 在Linux命令行下,要查看当前系统上有哪些用户登录,最直接、最常用的命令包括 who 、 w 和 users 。它们…

    2026年9月21日 用户投稿
    100
  • Word中如何快速截图?

    Word中如何快速截图?Word中如何快速截图?Word中如何快速截图?Word中如何快速截图?

    打开word文档,选择顶部菜单栏中的“插入”功能。 1、 选择后下方会显示相关选项,直接点击所需项即可完成操作。 2、 点击后进入选择界面,选取对应功能进行下一步。 3、 此时可以看到,所截取的图片已自动添加至Word文档中。 以上就是Word中如何快速截图?的详细内容,更多请关注创想鸟其它相关文章…

    2026年9月21日 用户投稿
    000
  • Linux如何限制用户执行特定命令

    Linux如何限制用户执行特定命令Linux如何限制用户执行特定命令Linux如何限制用户执行特定命令Linux如何限制用户执行特定命令

    首选sudo进行命令限制,因其灵活且可审计;通过visudo配置精确的用户权限,结合白名单、命令别名和!语法实现允许或拒绝特定命令;同时防范绕过手段如全路径执行、间接调用、脚本执行等,需多层防御并辅以日志监控。 在Linux环境中,限制用户执行特定命令,最直接有效且灵活的方法通常是利用 sudo 权…

    2026年9月21日 用户投稿
    100
  • Linux如何创建符号链接和硬链接

    Linux如何创建符号链接和硬链接Linux如何创建符号链接和硬链接Linux如何创建符号链接和硬链接Linux如何创建符号链接和硬链接

    符号链接是快捷方式,指向文件或目录路径,原文件删除后链接失效;2. 硬链接共享同一inode,不能跨文件系统或链接目录;3. 使用ln -s创建符号链接,ln创建硬链接;4. 符号链接可跨分区,硬链接删除原文件后仍可访问数据。 在Linux中,创建符号链接(软链接)和硬链接是管理文件和目录的常用操作…

    2026年9月21日 用户投稿
    000
  • Linux如何查看sudo执行的历史记录

    Linux如何查看sudo执行的历史记录Linux如何查看sudo执行的历史记录Linux如何查看sudo执行的历史记录Linux如何查看sudo执行的历史记录

    要追溯sudo执行的命令,需查看系统日志或配置sudo日志;在Ubuntu/Debian中查/var/log/auth.log,CentOS/RHEL中查/var/log/secure,或使用journalctl _COMM=sudo筛选;通过配置/etc/sudoers中的Defaults log…

    2026年9月21日 用户投稿
    300
  • 如何为VSCode安装新的字体?

    先在操作系统安装字体文件,再在VSCode设置中指定字体名称。1. Windows右键安装.ttf/.otf文件,macOS用字体册安装,Linux复制到~/.fonts并运行fc-cache -fv;2. VSCode中通过设置界面或编辑settings.json修改”editor.f…

    2026年9月21日
    000

发表回复

登录后才能评论
关注微信