Shell 脚本基础

Shell 脚本基础

💡 原文英文,约4500词,阅读约需17分钟。
📝

内容提要

本文介绍Linux Shell脚本基础,包括:脚本以#!/bin/bash开头,可用./或bash运行;支持单行#与多行:<<EOF注释;变量无需$定义,引用加$,可用readonly设为只读;字符串单引号不解析、双引号解析变量;数组用括号定义,下标从0开始;expr支持字符串、整数及逻辑运算;test与[]用于条件判断;流程控制含if、case、for、while、until及break、continue;函数用return返回0-255退出码,echo输出结果;exit退出脚本;重定向操作stdin、stdout、stderr;source可引入外部脚本。

🔎

延伸解读

变量作用域与脚本间通信

文章指出用户自定义变量(局部变量)不能被子进程访问,而环境变量(全局变量)可以。这意味着在脚本中定义的普通变量,在调用另一个脚本时不会自动传递。若需在脚本间共享数据,必须使用 export 将变量导出为环境变量,或通过 source 引入脚本。理解这一区别有助于避免变量未定义的错误,并合理设计脚本间的数据传递方式。

整数运算的局限与替代方案

文章强调 bash 只能进行整数运算,expr 命令会将操作数转换为整数,转换失败则报错。对于浮点数,bash 将其视为字符串,无法直接计算。虽然 expr 支持字符串操作和逻辑运算,但涉及小数时需借助其他工具。此外,$[] 和 $(()) 也仅支持整数运算,且 $[] 不支持浮点数和字符串。因此,在需要精确计算或浮点运算时,应考虑使用 bc 等外部命令。

函数返回值与输出捕获

文章说明 bash 函数的 return 返回的是 0-255 的退出码,而非函数结果。要获取函数的输出,需用 echo 打印到标准输出,再通过 $(function_name) 捕获。return 值可用 $? 获取。这种设计使得函数可以同时返回状态码和输出数据,但需注意退出码范围有限,且 $? 会覆盖前一个命令的退出码。在递归函数中,利用 $() 捕获 stdout 是实现结果传递的常用技巧。

条件判断中的空格与引号

文章提醒,使用 test 或 [] 进行条件判断时,每个组件之间必须有空格,变量最好用双引号括起来,常量用单引号或双引号。例如,当变量值包含空格时,不加引号会导致参数拆分,引发语法错误。正确写法是 [ "$name" == "timer ring" ]。此外,[] 是 test 的别名,[[]] 是增强版,但文章未深入其差异。遵循这些规则可避免常见的条件判断错误。

❓

Q&A

Shell脚本的第一行通常写什么?有什么作用?

第一行通常写 #!/bin/bash,用于指定脚本的解释器为 bash。

Shell脚本中如何定义变量和使用变量?

定义变量时不需要加 $,等号两边不能有空格,例如 name='timerring'。使用变量时需要在变量名前加 $ 或 ${},例如 echo $name 或 echo ${name}。

Shell脚本中单引号和双引号有什么区别?

单引号内的内容会原样输出,不执行命令也不解析变量;双引号内的内容可以执行命令和解析变量。

Shell脚本中如何定义数组和读取数组元素?

数组用括号定义,元素之间用空格分隔,例如 array=(1 abc "def" timerring)。读取元素使用 ${array[下标]},下标从0开始。

Shell脚本中if语句的语法是什么?

if 语句的基本语法为:if condition then 语句... fi。也可以有 else 或 elif 分支。condition 通常使用 test 或 [] 进行条件判断。

Shell脚本中如何定义和调用函数?

函数定义格式为:函数名() { 语句... },调用时直接写函数名,不需要括号。函数内可以用 return 返回0-255的退出码,用 echo 输出结果,通过 $? 获取返回值,通过 $(函数名) 获取输出。

🏷️

标签

➡️

继续阅读