Shell 三三两两(1)

在Shell脚本中或多或少遇到$1-$9 , $0 , $? , $! , $$ , $*, $# , [email protected] 这些特殊意义的命令符。如果你是一位初学者,那么恭喜你看它就像看老道写的符箓,有点摸不着边?是要死记硬背?还是理解一下再记忆呢?我想还是理解一下再记吧!

简要说明一下:

一、与参数相关: $1-$9 , $0 ,$# ,  $*, [email protected]

1)$1-$9   表给Shell的第几个参数:

  在计算机语言编写一段代码总会涉及到什么形参、实参,即一段代码需要传递参数来保持灵活性。那么我们在编写shell脚本时,实际上就是实现一段功能的脚本代码,为了应对脚本灵活性那么就需要参数,那么参数们在shell脚本中使用时总要一个编号吧,否则怎么知道你是第一个,他是第二个……。现在shell爸爸说了,$1就表示第一个参数,$2就表示第2个参数,以此类推到$9表示第9个参数了;那么还要给shell脚本第10个,第11个……怎么办?shell爸爸说前面我有点考虑不足,$10到底表示第一参数$1值再加个0呢?还是第10个参数?所以shell规定了,要表示第10个,第11个……用${}包围起来,${10}表示第10个参数,${11}表示第11个参数,……以此类推。

2) $0 表示执行本Shell的脚本/命令的名称。

  前面$1-$9表示给shell脚本的第几个参数,那么谁需要这些参数呢?这不简单,还有谁要啊?不就是我们编写的shell脚本需要参数嘛!那么$0就是表示这位需要参数的shell脚本奶爸。也正因为这shell奶爸需要参数,所以也就在$0这奶爸的带领下有了$1,$2……$9一群参数。下面编写一个shell脚本说明一下$0和$1-$9:

 1 [[email protected] ~]# mkdir /shell
 2 [[email protected] ~]# cd  /shell
 3 [[email protected] shell]#vim myPapaShell.sh
 4 #!/bin/bash
 5
 6 echo "IamPapa:$0"
 7 echo "IamParameter1: $1"
 8 echo "IamParameter2: $2"
 9 echo "IamParameter3: $3"
10
11 [[email protected] shell]#chmod +x myPapaShell.sh
12 [[email protected] shell]#./myPapaShell.sh firstPara  secondPara thirdPara
13 IamPapa: ./myPapaShell.sh
14 IamParameter1: firstPara
15 IamParameter2: secondPara
16 IamParameter3: thirdPara

3)$# 表示传给shell脚本的参数个数,即传了几个参数给shell脚本(#符号看上去有点像算盘)。

现在shell脚本奶爸不好当啊,有些时候它能量大一下子聚了好多参数,有时候能量不足,只聚了两三只小猫。shell脚本老爸这下犯愁了,谁知道给我传了多少个参数。这时$#手拿大算盘噼里啪啦就给shell脚本老爸知道现在有多少个参数。

4)$* 和[email protected] 表示所有参数列表

当看到*符号时,就想到所有。特别在匹配中表示任意字符就全部概念;而看到@就想到微信、QQ中@all,而shell脚本中又能@谁?@只能是参数。$* 和[email protected] 都是列举出所有传给shell脚本奶爸的参数。但是$* 和[email protected]还是存在区别,区别如下:

$* 和 [email protected] 都表示传递给函数或脚本所有参数不被双引号(" “)包含时,都以"$1"  "$2"……"$n"的形式输出所有参数。

但是当$* 和 [email protected]被双引号(" “)包含时不同了"$*" 会将所有的参数作为一个整体,以"$1 $2 …$n"的形式输出所有参数;而"[email protected]" 则会将各个参数分开,以"$1" "$2"……"$n"的形式输出所有参数。[email protected]就像微信和QQ中@一样,不仅支持@all还能@各分开的参数。

下面列举一个shell脚本说明$# ,$* ,[email protected]

[[email protected] shell]# cd /shell
[[email protected]-jumperserver shell]# vim myParaShell.sh
#!/bin/bash

echo "Count the Parameter: $#"

echo ‘######       $*      ########‘
for i in $* ;do
let j++
echo "Parameter$j: $i"
done

j=0
echo ‘######       [email protected]      ########‘
for i in [email protected] ;do
let j++
echo "Parameter$j: $i"
done

j=0
echo ‘######       "$*"    ########‘
for i in "$*" ;do
let j++
echo "Parameter$j: $i"
done

j=0
echo ‘######      "[email protected]"      ######‘
for i in "[email protected]" ;do
let j++
echo "Parameter$j: $i"
done

[[email protected]-jumperserver shell]# chmod +x myParaShell.sh
[[email protected]-jumperserver shell]# ./myParaShell.sh first
Count the Parameter: 1
######       $*      ########
Parameter1: first
######       [email protected]      ########
Parameter1: first
######       "$*"    ########
Parameter1: first
######      "[email protected]"      ######
Parameter1: first
[[email protected]-jumperserver shell]# ./myParaShell.sh first second
Count the Parameter: 2
######       $*      ########
Parameter1: first
Parameter2: second
######       [email protected]      ########
Parameter1: first
Parameter2: second
######       "$*"    ########
Parameter1: first second
######      "[email protected]"      ######
Parameter1: first
Parameter2: second

二、与进程号PID相关 $$ , $!

1) $$ 表示shell脚本运行的当前进程PID号。

2) $! 表示shell脚本最后运行的后台进程的PID(通过jobs查看的后台进程),即后台运行的最后一个进程的进程PID号。

  :$! 仅仅针对在运行本shell脚本中的后台进程的PID记录,它是一个局部变量的概念。通俗讲如果shell脚本中含有$!,那么它只记录当前shell脚本运行期间开启的最后一个后台进程PID。shell脚本之后台进程变化它一律不管,相互隔离。($1-$9 , $0 , $? , $! , $$ , $*, $# , [email protected] 都是局部变量个概念,都是只记录当前shell脚本运行期间内容值。)

  :即使现在jobs中已经没有后台进程了,如执行完毕等,$!还会保留最后一个(最新一次加入的)后台运行进程的PID号,直到有最新的后台进程加入时才会更新$!。

 1 [[email protected] shell]# vim myProcShell.sh
 2 #!/bin/bash
 3
 4 echo "the shell script PID: $$"
 5
 6 sleep 600 &
 7 sleep 60 &
 8 echo "the last job PID: $!"
 9 [[email protected] shell]# chmod +x myProcShell.sh
10 [[email protected] shell]# ./myProcShell.sh
11 the shell script PID: 5861
12 the last job PID: 5863
13 [[email protected]jumperserver shell]#
14 [[email protected] shell]# cp myProcShell.sh myProcShell1.sh
15 [[email protected] shell]# vim myProcShell1.sh
16 #!/bin/bash
17
18 echo "the shell script PID: $$"
19
20 echo "the last job PID: $!"
21 [[email protected] shell]# chmod +x myProcShell1.sh
22 [[email protected] shell]# sleep 600 &
23 [1] 5893
24 [[email protected] shell]# ./myProcShell1.sh
25 the shell script PID: 5894
26 the last job PID:                       #$!仅针对运行的本shell的后台进程PID记录。
27 [[email protected] shell]# 

三、结束代码   $?

1) $?  表示最后运行的命令的结束代码(返回值),即执行上一个指令的返回值(显示最后命令的退出状态)

 其中指令的返回值:

    0    :表示正常,没有错误。

    其他值(非0) :表示是有错误,具体是什么错误查看该指令的帮助。  

[[email protected] shell]# vim myCommandShell.sh
#!/bin/bash

echo "last command status: $?"

num=2
[ $num -lt 3 ]
echo "$num < 3:$?"
[ $num -gt 3 ]
echo "$num > 3:$?"
[[email protected]-jumperserver shell]# chmod +x myCommandShell.sh
[[email protected]-jumperserver shell]# x=2
[[email protected]-jumperserver shell]# [ $x -lt 0 ]
[[email protected]-jumperserver shell]# ./myCommandShell.sh
last command status: 0
2 < 3:0
2 > 3:1
[[email protected]-jumperserver shell]# [ $x -lt 0 ]
[[email protected]-jumperserver shell]# echo $?
1
[[email protected]-jumperserver shell]#

小结:

  $1-$9 , $0 , $? , $! , $$ , $*, $# , [email protected] 都是局部变量概念,只记录当前shell脚本运行期间的内容。在这些内容中可以把分层三类:与参数相关的,与进程相关的 和 与指令结束代码相关的。

参考:

https://blog.csdn.net/baidu_28126759/article/details/87863361

https://blog.csdn.net/xgt_520/article/details/78738320

https://www.runoob.com/linux/linux-shell-passing-arguments.html

原文地址:https://www.cnblogs.com/gageshen/p/11563910.html

时间: 2024-11-14 11:35:37

Shell 三三两两(1)的相关文章

【Linux系列】【基础版】第四章 Shell基础之正则表达式

4. Shell基础之正则表达式     4.1 正则就是一串有规律的字符串         4.1 grep              4.1.1 格式: grep [-cinrvABC] 'word' filename             4.1.2 -c //count,表示行数             4.1.3 -i //不区分大小写             4.1.4 -n  //显示行号             4.1.5 -r  //遍历所有子目录             4

linux Shell函数

Shell函数类似于Shell脚本,里面存放了一系列的指令,不过Shell的函数存在于内存,而不是硬盘文件,所以速度很快,另外,Shell还能对函数进行预处理,所以函数的启动比脚本更快. 1.函数定义 1 2 3 4 function 函数名() {     语句     [return] } 关键字function表示定义一个函数,可以省略,其后是函数名,有时函数名后可以跟一个括号,符号"{"表示函数执行命令的入口,该符号也可以在函数名那一行,"}"表示函数体的结

Shell实现跳板机,为什么用跳板机

整理自:http://blog.chinaunix.net/uid-22101889-id-3167454.html 注意:请谨慎使用,到现在为止,使用了,我还没找到改回去的方法. 1.     问题 第一.很多大公司的服务器都不允许直接登录,而是通过一个跳板机才能登录过去.在跳板机中,通常只能执行几个少数命令(如SSH),而其他命令是不允许执行的,那么怎样才能实现这个功能呢? 第二.一些小公司,由于服务器比较少,不需要什么跳板机之类的说法,公司的开发运维人员加起来也就那么十几二十人,通常大家都

linux shell基础语法

1.第一个Shell脚本 打开文本编辑器,新建一个文件,扩展名为sh(sh代表shell),扩展名并不影响脚本执行,见名知意就好,如果你用php写shell 脚本,扩展名就用php好了. 输入一些代码: #!/bin/bash echo "Hello World !" "#!" 是一个约定的标记,它告诉系统这个脚本需要什么解释器来执行,即使用哪一种Shell.echo命令用于向窗口输出文本. 运行Shell脚本有两种方法. 1.1作为可执行程序 将上面的代码保存为t

shell中test命令方法详解

test命令用法.功能:检查文件和比较值 1)判断表达式 if test  (表达式为真) if test !表达式为假 test 表达式1 –a 表达式2                  两个表达式都为真 test 表达式1 –o 表达式2                 两个表达式有一个为真 2)判断字符串 test –n 字符串                                   字符串的长度非零 test –z 字符串                          

shell脚本

-e filename 如果 filename存在,则为真 [ -e /var/log/syslog ]-d filename 如果 filename为目录,则为真 [ -d /tmp/mydir ]-r filename 如果 filename可读,则为真 [ -r /var/log/syslog ]-w filename 如果 filename可写,则为真 [ -w /var/mytmp.txt ]-x filename 如果 filename可执行,则为真 [ -L /usr/bin/gr

20.5 Shell脚本中的逻辑判断;20.6 文件目录属性判断;20.7 if特殊用法;20.8 20.9 cace判断(上下)

扩展: select用法 http://www.apelearn.com/bbs/thread-7950-1-1.html 20.5 Shell脚本中的逻辑判断 格式1:if 条件 ; then 语句; fi 1. 创建if1.sh测试脚本: [[email protected] ~]# vi if1.sh a=5,如果a大于3,满足这个条件,显示ok 添加内容: #!/bin/bash a=5 if [ $a -gt 3 ] then echo ok fi 2. 执行if1.sh脚本: [[e

20.1 Shell脚本介绍;20.2 Shell脚本结构和执行;20.3 date命令用法;20.4 Shell脚本中的变量

20.1 Shell脚本介绍 1. shell是一种脚本语言 aming_linux blog.lishiming.net 2. 可以使用逻辑判断.循环等语法 3. 可以自定义函数 4. shell是系统命令的集合 5. shell脚本可以实现自动化运维,能大大增加我们的运维效率 20.2 Shell脚本结构和执行 1. 开头(首行)需要加: #!/bin/bash 2. 以#开头的行作为解释说明: 3. 脚本的名字以.sh结尾,用于区分这是一个shell脚本 4. 执行.sh脚本方法有两种:

shell 中seq的用法 echo -n用法

用法:seq [选项]... 尾数 或:seq [选项]... 首数 尾数 或:seq [选项]... 首数 增量 尾数 从1循环到100的两种方法(bash 其它的shell没试过)for x in `seq 1 100`;do echo $x;donefor x in {1..100};do echo $x;done echo -n 不换行输出 $echo -n "123" $echo "456" 最终输出 123456 echo -e 处理特殊字符 若字符串中