Android之路

导航

学习《Shell脚本学习指南 中文PDF版》的摘要笔记

    在日常开发中,代码管理等使用的都是终端命令,目前我使用的是XShell。除了代码管理(拉取、修改、提交等),版本编译等,或多或少涉及一些shell的常用命令。而前段时间有时间学习了一下《Shell脚本学习指南 中文PDF版》,并作了笔记。该书的教程说明见http://www.linuxidc.com/Linux/2013-01/77279.htm    以下记录的笔记一个标题可能对应的是书中的几个章节的汇总(我觉得重要或常用的),而非单独一章,感兴趣的可以下载PDF进行详细学习。本文还结合了菜鸟教程中的一些内容https://www.runoob.com/linux/linux-shell-variable.html

一、Shell脚本:

    Shell脚本的三大特性:

    简单性:高级解释型语言,可以简洁的表达复杂的操作。
    可移植性:使用POSIX定义的功能,使得脚本无需修改就可在不同系统上执行。
    易开发:耗时短。即短时间内就可以完成一个功能强大又好用的脚本。

    Shell脚本一般以#!/bin/sh开始,#!的长度限制63~1024字符,尽量不要超过64,各个系统限制有所区别。且#!前后不能有空格等其他字符,否则,执行脚本失败"-bash: ./finduser: bin/sh: bad interpreter: No such file or directory"

    #! 告诉系统其后路径所指定的程序即是解释此脚本文件的 Shell 程序。

简单脚本开发步骤:以统计当前用户数为例
$ cat > sfile         //创建文件sfile
who | wc -l          //统计命令
Ctrl+D               //end-of-file,即退出文件
$ chmod +x sfile      //赋予文件可执行权限
$ ./sfile             //执行

二、Shell命令:

    Shell识别三种基本命令:

    内建命令:Shell本身所执行的命令,为了其必要性和效率,例:cd、 read 、test、echo、 printf等。

    Shell函数:功能健全的一系列程序代码,以Shell语言写成,它们可以像命令那样引用。

    外部命令:由Shell的副本(新的进程)所执行的命令。以下为外部命令执行的流程图。

1、其他常用命令:

who:当前系统上登录用户
echo:标准输出
printf:与echo相比,需要在结尾使用\n换行.
基本的I/O重定向:标准输入/输出(<)、标准错误输出(>)----默认三者在终端
tr:translate的简写,主要用于压缩重复字符,删除文件中的控制字符以及进行字符转换操作。
   -s:压缩字符
   -d:删除字符
   -t:字符替换,可以省略
   格式:echo "abcddel" | tr -d "d"  ====> adcel
|:建立管道,program1|program2   //前一个的标准输出为后一个的标准输入
#:注释

grep:查找可配合+正则表达式(略),具体参考:http://www.cnblogs.com/ggjucheng/archive/2013/01/13/2856896.html
格式:grep "" filename

cut:切分文件,具体参考:http://www.cnblogs.com/xqzt/p/5858309.html

awk:一个强大的文本分析工具。

 三、Shell变量:

     不需要声明类型,直接创建即可。以下两个命令提供对变量的管理:    

    export:用于修改或打印环境变量。
    readonly:只读,使得变量不得修改。

  一个简单的例子,创建变量:

#创建变量var
var="Java and Android or Shell"

#显示变量的值
echo $var
echo ${var}
echo _${var}_

  创建变量时,等号两边不能存在空格(注:与其他编程语言不同)。变量的命名规则如下:  

  • 命名只能使用英文字母,数字和下划线,首个字符不能以数字开头。
  • 中间不能有空格,可以使用下划线(_)。
  • 不能使用标点符号。
  • 不能使用bash里的关键字(可用help命令查看保留关键字)。

1、POSIX Shell中其他的内置变量:显示时都是$...

?:前一个命令的退出状态
$:Shell进程的进程编号(process ID)
0:Shell程序的名称
!:最近一个后台命令的进程编号.
IFS:内部的字段分隔器.例如单词分隔,一般为空格、制表符或换行.
HOME:根目录
LANG:当前locale的默认名称
PATH:命令的查找路径
PPID:父进程的进程编号
PWD:当前工作目录

2、POSIX Shell的结束状态:

0:命令成功退出
>0:在重定向或单词展开期间
1-125:命令不成功地退出
126:命令找到了,但文件无法执行
127:命令找不到
>128:未定义
可以使用exit命令传递一个退出值给它的调用者,退出脚本。

四、Shell中的运算符及位置参数等:

1、替换运算符:

${var:-word}:若var存在且非null,则返回其值;否则,返回word.
用途:若变量未定义,返回默认值.
${var:
=word}:若var存在且非null,则返回其值;否则,设置其为word,并返回值. 用途:若变量未定义,设置默认值.
${var:
?message}:若var存在且非null,则返回其值;否则,显示var:message,并退出当前命令或脚本. 用途:为了捕捉由于变量未定义所导致的错误.
${var:
+word}:若var存在且非null,则返回word;否则,返回null. 用途:为测试变量的存在. 例如:若count已定义,则${count:+1}返回1.

2、模式匹配运算符:

${path#/*/}
${path%.*}
原则:#匹配的是前面(左),%匹配的是后面(右).
/*/,匹配任何位于两个斜杠之间的元素;.*,匹配点号之后接着的任何元素.
${#var}:返回var值里的字符串长度.

3、位置参数:

  Shell脚本中的命令行参数;同时也表示Shell函数中的函数参数。其名称由单个整数命名,且当这个整数大于9时,需{}。例如:

echo arg1 is $1    
echo arg10 is ${10}    //表示命令行的第10个参数
$#:统计参数总数.
$*、$@:将所有命令行参数视为单个字符串.
"$*":带双引号,将所有命令行参数视为一个字符串.
"$@":带双引号,保留真正的参数值,即显示正确的参数.【正确显示命令行参数】
shift:截去来自列表的位置参数,由左开始.默认shift等同于shift 1,即将第一个参数移除
例:    shift 10:截去第10个参数,若总数不足10个,则该语句不起作用
简单的循环语句:
for i in "$@" do echo i is $i done

4、判断语句:

if -- then -- elif -- else --fi
写判断条件时,语法格式必须((...)),若以否定状态表达,则在条件前加入!即可.
例如:

i
=168 if ((i<10)) then echo "<10" elif ((i<200)) then echo "<200" else echo "fail" fi

5、test命令:用来测试文件属性、比较字符串及数字。

格式: test [ ... ] 或[[ ... ]] 第二种格式时,表达式与[]中间必须用空白符隔开

str
=5 str2=6 if test $str = $str2 then echo "===" elif [[ $str<$str2 ]] then echo "<" echo fail fi

6、case语句:每个条件用)结尾,且;;表示结束,类似java中的break,*表示默认匹配模式,类似java中的default。

case $1 in     
    10)
    echo "10"        
    ;;    
    2)
    echo "2"    
    ;;        
    *)
    echo "other"    
    ;;
esac

7、getopts:处理输入参数/命令行的选项。

8、$((...)):Shell中的算术运算。

9、Shell中自增的几种格式:

  • ((count++))
  • let count+=1
  • let count++
  • count=$((count+1)) //((...)),推荐--新写法
  • count=`expr $((count+1))` //``反引号,而非单引号,原始形式

10、通配符:

?:任何的单一字符
*:任何的字符字符串
[set]:任何在set里的字符
[!set]:任何不在set里的字符

五、输入/输出、文件与命令执行:

1、标准输入、输出、标准错误输出:

0:标准输入】
【1:标准输出】
【2:标准错误输出】
read [-r] variable:将信息读入一个或多个Shell变量.
-r:原始读取,不将行结尾处的反斜杠解释为续行字符.

2、重定向:

<:以只读模式打开文件
>:以只写模式打开文件
>>:追加

例:    2>&1,将标准错误输出重定向到标准输出.

3、Shell中的.bat文件就是一个可执行文件,双击该文件即可弹出终端运行,执行其中的命令。类似刷机文件update_all.bat

例:
set update="update_test"
echo %update%
pause                //执行完命令后暂停,提示用户按任意键退出,而非直接退出.

4、隐藏文件(.file),只是个习惯用法,在用户层面的软件上它是这样的,但核心程序(kernel)并不认为开头带有点号的文件与其他文件有不同。

5、嵌套命令:

for i in $(cd bin;echo vartest)   //找到bin目录下的vartest文件
do    
    diff -c bin/$i $i    #第二个$i 表示当前目录下的文件$i 
done | more

6、head命令:显示文件的前n行

head -n 10 file        //显示名为file的文件的前10行

7、set命令:

  主要是显示系统中已经存在的shell变量,以及设置shell变量的新变量值。set命令不能够定义新的shell变量。如果要定义新的变量,可以使用declare命令以 变量名=值 的格式进行定义即可。

    -a  标示已修改的变量,以供输出至环境变量。
    -b  使被中止的后台程序立刻回报执行状态。
    -C  转向所产生的文件无法覆盖已存在的文件。
    -d  Shell预设会用杂凑表记忆使用过的指令,以加速指令的执行。使用-d参数可取消。
    -e  若指令传回值不等于0,则立即退出shell。
    -f   取消使用通配符。
    -h  自动记录函数的所在位置。
    -H Shell  可利用"!"加<指令编号>的方式来执行history中记录的指令。
    -k  指令所给的参数都会被视为此指令的环境变量。
    -l  记录for循环的变量名称。
    -m  使用监视模式。
    -n  只读取指令,而不实际执行。
    -p  启动优先顺序模式。
    -P  启动-P参数后,执行指令时,会以实际的文件或目录来取代符号连接。
    -t  执行完随后的指令,即退出shell。
    -u  当执行时使用到未定义过的变量,则显示错误信息。
    -v  显示shell所读取的输入值。
    -x  执行指令后,会先显示该指令及所下的参数。
    +<参数>  取消某个set曾启动的参数。

  执行脚本时,可以使用以下命令跟踪:

set -x :打开执行跟踪的功能,这会使得Shell显示每个被执行的命令,并在前面加上“+”
set +x :关闭跟踪

六、总结:

  关于Shell的常用命令及基本用法已经介绍完,其他的文件处理、进程等章节并未在本文显示,感兴趣的可阅读PDF,后续根据需要可能会进行补充。

 

posted on 2019-07-30 10:24  Android之路  阅读(1641)  评论(0编辑  收藏  举报