写点什么

shell 养成计划之易筋经篇(持续更新)

作者:晴天
  • 2022 年 8 月 12 日
    广东
  • 本文字数:10302 字

    阅读完需:约 34 分钟

shell养成计划之易筋经篇(持续更新)

标题:shell 脚本养成计划

1、shell 篇

1.1、变量

1.1.1、特殊变量

  • #!:指定如下解释程序是一个可执行文件,需要指定的的 shell 去运行它;

  • $?:每一个命令都有自己的返回值,为 0 表示成功异常,非 0 则表明执行异常;

  • $0:当前执行脚本的名称,或者也可以看作执行命令的第一个参数(即脚本文件);

  • $1-9:脚本执行时,依次传递的参数 1-9;

  • $#:脚本执行时,传递参数的个数;

  • $*:输入参数的具体内容,(将多个参数并作一个单词处理);

  • $@:输入参数的列表对象;

  • $$:当前进程的 PID;

  • $!:上一个后台进程的 PID


如下所示:测试脚本。执行:bash 1.sh hah heh hihi


#!/bin/bash
systemctl restart docker.serviceecho "\$?: $?"echo "\$0: $0"echo "\$1: $1, \$2: $2, \$3: $3"echo "\$#: $#"echo "\$*: $*"arr=$@for "${str}" in ${arr}; do echo "${"${str}"}"; done
复制代码


测试查看运行的对应结果。

1.1.2、普通变量

  • name=ike,定义普通变量,只在当前 shell 中有效;


变量的引用方式(上下文同)


  • {key}:可以解决歧义,${#key}:输出变量值的定义长度;

  • 'key":单引号输出为 $key,双引号则为变量值;


[root@VM-218-88-centos ~/]# name=hehe[root@VM-218-88-centos ~/]# echo "$name"hehe[root@VM-218-88-centos ~/]# echo '$name'$name
复制代码

1.1.3、环境变量

  • export name=ike;定义系统的环境变量,在当前 shell 和其他子 shell 中都可以引用;

  • env,查看当前 shell 全体的环境变量;

  • unset name,清除指定的环境变量;

  • source xxx.sh,在当前 shell 中执行脚本,可以引用当前 shell 所有变量;

1.2、排序与或

  • ; :命令的排序执行,无论成功失败与否

  • && :逻辑与,按照命令排序的顺序,成功后进入下一个命令的执行;

  • || :逻辑或,按照命令排序的顺序,失败后进入下一个命令的执行;


如下所示:


[root@VM-218-88-centos /]# go tls_test_0.js ; echo "success"go tls_test_0.js: unknown commandRun 'go help' for usage.success[root@VM-218-88-centos /]# go tls_test_0.js && echo "success"go tls_test_0.js: unknown commandRun 'go help' for usage.[root@VM-218-88-centos /]# go tls_test_0.js || echo "success"go tls_test_0.js: unknown commandRun 'go help' for usage.success
复制代码

1.3、重定向

  • 覆盖:> :标准输出的结果覆盖目标文件;

  • 追加:>>:标准输出的结果追加到目标文件;

  • 覆盖:2>:错误输出的结果覆盖目标文件;

  • 追加:2>>:错误输出的结果追加到目标文件;

  • 合并:&>:标准和错误信息都直接覆盖目标文件;

  • 合并:&>>:标准和错误信息都直接追加目标文件;

  • <:将目标文件的内容作为执行命令的输入参数

  • <<END:从标准键盘(控制台)中读取数据,换行分隔,直到遇见分界符 END 才终止(分界符可以是任意自定义字符串)

  • &>/dev/null:清空命令的输出,即不要它,/dev/null,磁盘特殊块,可以看作黑洞,永久为空


特殊使用:command < file > 1.log,将 file 作为命令的输入参数,然后将执行结果输出到 1.log


如下所示:执行一个 mongo 批量操作数据的脚本,然后操作记录输出到 1.log 文件中;


docker exec -i mongo mongo < mongo_update.js > 1.log
复制代码

1.4、cat 还是 tac

tac 是 cat 的反过来,所以其功能与 cat 类似却是相反,eg:tac 文件是倒过来的从下往上,用法不常见;


cat :连接文件,或者标准输入并打印好,主要有三大功能:


  1. 一次显示整个文件的内容:cat fileName;

  2. 创建一个新文件,并从键盘完成输入:cat > fileName;

  3. 将多个文件内容合并为一个文件,或者连接起来查看:cat file1 file2 > newfile


参数用法:


  • -n:--number,对输出的所有行进行编号,从 1 开始;

  • -s:--squeeze-blank,有连续两行以上的空台,就替换为一行;

  • -b:--number-nonblank,对空行输出编号,从 1 开始;

  • -E:--show-ends,在每行结束处显示 $;


1、创建一个 sh 文件,并嵌入内容(注意,嵌入的 $需要转译处理):


[root@VM-218-88-centos /]# cat > test.sh <<END> #!/bin/bash> p=\$1> echo \${p}> END[root@VM-218-88-centos /]#
复制代码


2、对文件内容加上行号然后


[root@VM-218-88-centos /]# cat -n test.sh > test_new.sh[root@VM-218-88-centos /]# cat test_new.sh      1  #!/bin/bash     2  p=$1     3  echo ${p}
复制代码


3、去掉行号复原($被识别到了,还是不要对.sh 文件这么用,此处只是测试)


[root@VM-218-88-centos /]# cat test_new.sh | awk '{print $2}' > test_new2.sh [root@VM-218-88-centos /]# cat test_new2.sh #!/bin/bashp=$1echo
复制代码

1.5、软件包管理

1.5.1、rpm

软件包管理工具,根据提供的.rpm 源代码文件自动编译、安装;


  • -i:--install,安装(指定源文件);

  • -v:--verbose,显示详细信息,

  • -h:--hash,显示进度;eg:安装时显示进度及详细信息,rpm -ivh xxxx.rpm

  • --nodeps:不检测依赖性;

  • -U:upgrade,升级包;

  • -e:erase,卸载指定包;

  • -q:查询是否安装(以下皆须配合-q 使用);

  • -a:所有,eg:查询已经安装的所有 rpm 包:rpm -qa

  • -i:查询软件信息,eg:查询指定包信息:rpm -qi python-javapackages-3.4.1-11.el7.noarch

  • -l:列表,eg:查看包安装位置:rpm -ql trousers-0.3.13-1.el7.x86_64

  • -f:查询系统文件属于哪个 rpm 包:rpm -qf 系统文件名

  • -R:检测包的依赖性,rpm -qR 包名


注意:涉及依赖性问题的话,需依次解决(安装,正向逐个安装,卸载,反向逐个卸载)


[root@localhost Packages]# rpm -e httpd错误:依赖检测失败:        httpd = 2.4.6-67.el7.centos 被 (已安裝) httpd-devel-2.4.6-67.el7.centos.x86_64 需要[root@localhost Packages]# rpm -e httpd-devel [root@localhost Packages]# rpm -e httpd
复制代码

1.5.2、yum

基于 rpm 包管理,能够从指定的服务器自动下载 rpm 包安装,并且自动处理好依赖关系,一次性的安装所有依赖的软件包,无需繁琐的逐个处理:yum [options] [command] [packages……]


[root@VM_0_15_centos ~]# cd /etc/yum.repos.d/[root@VM_0_15_centos yum.repos.d]# lsCentOS-Base.repo  CentOS-Epel.repo  docker-ce.repo  mysql-community.repo  mysql-community-source.repo  yarn.repo
复制代码


如果系统能够联网,使用默认的网络源文件 CentOS-Base.repo,


![image-20220807225752803](/Users/wangjinchao/Library/Application Support/typora-user-images/image-20220807225752803.png)


  • gpgcheck:1 指 RPM 的数字证书生效,写成 0 就是不生效;

  • gpgkey:数字证书的公钥文件保存位置。

  • enable:此容器是否生效(1),默认生效;

  • baseurl:yum 源服务器的地址。

  • name:说明


配置文件见/etc/yum.conf,各项操作命令如下:


  • yum list:列出所有可安装的列表;

  • yum check-update:列出所有可更新的软件列表;

  • yum update :更新所有软件;

  • yum install -y <packageName>:安装指定软件,-y:自动 yes,下同;

  • yum update -y <packageName>:更新指定软件

  • yum remove -y <packageName>:卸载

  • yum search 关键词:查找

  • yum clean packages:清除缓存目录下的软件包

  • yum clean headers:清除缓存目录下的 headers

  • yum clean oldheaders: 清除缓存目录下旧的 headers

  • yum clean:yum clean all,皆等于:yum clean packages && yum clean oldheaders


软件组:


  • yum grouplist:列出所有可用的软件组列表

  • yum groupinstall <groupName>:安装指定软件组

  • 卸载,更新……类似

1.6、管道

与重定向不同的是,管道可以将两个甚至多个不同的命令(程序或者进程)连接到一起,将上一个命令的输出作为下一个命令的输入,依次执行,连接方式为|,称为管道符。即:它改变了数据输入输出的方向


下一个命令只能处理上一条命令正确的输出,


1、查找文件中 xxxx 内容:cat fileName |grep 'xxxx';


2、查找 xxxx 相关服务列表:systemctl list-units |grep xxxx


3、假如知道日志文件的结构,要筛选它指定分隔列表的带有web内容字段:


[root@VM-218-88-centos /]# cat 20220808.access_12.csv |awk -F , '{print $2}' |grep "web""rio3_internal_web""rio3_internal_webapi""rio3_internal_web""rio3_internal_web""rio3_internal_webapi""rio3_internal_web""rio3_internal_webapi"
复制代码

1.7、条件判断

1.7.1、if

基本语法:


if [command]; then   # 符合该条件的执行语句fi
if [ command ];then # 符合该条件执行的语句elif [ command ];then # 符合该条件执行的语句else # 符合该条件执行的语句fi
复制代码


  • command可以是条件,也可以是执行命令(中括号两边必须要有空格,强制),如果 command 为命令执行后,返回的 $? = 0,那么往下执行 then,否则跳到下一个判断或者跳出 if,

  • then 和 fi 是分开的语句,如果要在一行展示,则它俩之间必须要有分号隔开;

  • 条件判断对于变量之间的比对需要加双引号,方便处理;

  • 单独使用><(大于小于)时,会被当成命令的重定向,需要使用 &gt,&lt 转译代替;

  • 使用-z 或者-n 来检查长度的时候,没有定义的变量也为 0,所以:空变量和没有初始化的变量可能会干扰 shell,在不确定变量的内容的时候,可以使用-n 或者-z 提前判断一下;

  • 条件可以是双圆括号(( )):表示数学表达式,允许在比较中进行简单的算术操作,双圆括号里面的'>','<'号不需要转意;

  • 条件可以是双方括号[[ ]]:表示高级字符串处理函数,使用标准的字符串比较,还可以使用匹配模式,从而定义与字符串相匹配的正则表达式。


常用针对文件的条件判断


  1. [ -a file ]: 如果 file 存在则为真。

  2. [ -d file ]: 如果 file 存在且是一个目录则返回为真。

  3. [ -e file ]: 如果 指定的文件或目录存在时返回为真。

  4. [ -f file ]: 如果 file 存在且是一个普通文件则返回为真。

  5. [ -r file ]: 如果 file 存在且是可读的则返回为真。

  6. [ -w file ]: 如果 file 存在且是可写的则返回为真。(一个目录为了它的内容被访问必然是可执行的)

  7. [ -x file ]: 如果 file 存在且是可执行的则返回为真。


字符串判断


  1. [ -z "${str}" ] :如果 str 的长度为零则返回为真,即空是真;

  2. [ -n "${str}" ] :如果 str 的长度非零则返回为真,即非空是真;

  3. [ "${str}" ] :如果字符串不为空则返回为真,与-n 类似;

  4. [ "{str2}" ]: 如果两个字符串相同则返回为真;

  5. [ "{str2}" ]: 如果字符串不相同则返回为真;


逻辑判断


  1. [ ! expr ] :逻辑非,如果 expr 是 false 则返回为真。

  2. [ expr1 -a expr2 ] :逻辑与,如果 expr1 and expr2 全真则返回为真。

  3. [ expr1 -o expr2 ] :逻辑或,如果 expr1 或者 expr2 为真则返回为真。

  4. [ ] || [ ] :两个条件取或,用 OR 来合并两个条件

  5. [ ] && [ ] :两个条件取与,用 AND 来合并两个条件


1、判断一个目录(文件夹)是否存在,不存在的话创建


#!/bin/bashif [ ! -d "$1" ];then  mkdir -pv "$1"fi
复制代码

1.7.2、while

都是条件判断执行,while 用于循环,基本语法:


while conditiondo    statementsdone
复制代码


condition:与上文的 if 类似,同理 do 和 done 是分开的语句,如果要在一行展示,则它俩之间必须要有分号隔开;


1、如下所示(1~100 的累加):


shell 中,默认都是字符串操作。(())声明内部为算术表达式,变量引用不需


#!/bin/bash
# (())用法,表明内部为算术表达式,变量引用不需$i=0num=0while ((i <= 100))do ((num+=i)) ((i+=1))doneecho "1+2+3+……+100=$num"
# []:变量引用必须加""i=0num=0while [ "$i" -le 100 ]do let num+=i; let i+=1doneecho "1+2+3+……+100=$num"
# [[]]:使用标准的字符串比较,无需给变量引用添加""i=0num=0while [[ $i -le 100 ]]do let num+=i; let i+=1doneecho "1+2+3+……+100=$num"
复制代码

1.8、文本处理利器

1.8.1、awk

优秀的智能文本处理工具:打印文件中的某一列,它会智能的去切分数据,不管是 tab,还是空格……或者指定分隔符;


  • -F:指定分隔符,eg:指定分隔符为,:-F ","

  • -v:指定变量和默认值;

  • $NF:代表最后一个字段;

  • NR:代表第几行;

  • FS:输入分隔符(即-F 的意思);

  • OFS:输出字段分隔符;

  • RS:输入记录分隔符;

  • $0:显示整行;

  • 1…N:第一个字段到第 N 个字段;


eg:查找用户名列表:


[root@VM-218-88-centos /]# cat /etc/passwd |awk -F ":" '{print $1}'rootbindaemon
复制代码


指定行号,采用变量自增,打印最后一列($NF)


[root@VM-218-88-centos /]# cat /etc/passwd |awk -F ":" -v "i=0" '{i++;print i,$NF}'1 /bin/bash2 /sbin/nologin3 /sbin/nologin4 /sbin/nologin
复制代码


根据上文,打印第 33 行的最后一列(NR==33):


[root@VM-218-88-centos /]# cat /etc/passwd |awk -F ":" 'NR==33{print $NF}'/sbin/nologin
复制代码


输出字段的分隔符(OFS="--";),一般与-F(或者 FS)配合使用,重新定义内容的分隔:


[root@VM-218-88-centos /]# cat /etc/passwd |awk -F ":" -v "i=0" '{OFS="--";i++;print i,$NF,$1}'1--/bin/bash--root2--/sbin/nologin--bin3--/sbin/nologin--daemon4--/sbin/nologin--adm
复制代码


优先级判定


  • BEGIN:最高优先级,最先执行,位于 PROGRAM 之前,不依赖数据源;

  • PROGRAM:默认,对数据流操作的,必选(默认)代码块;

  • END:处理数据流之后,如果需要 END,就必须事先有 PROGRAM 的支持


注意:如果只用 BEGIN 或者 END,然后跟上数据源是没有效果的,数据源只对 PROGRAM 生效


如下所示:


# BEGIN后面不需要加任何数据源,也可以打印内容[root@VM-218-88-centos /]# awk -v "name=ike" 'BEGIN{print name}'ike[root@VM-218-88-centos /]# awk -v "name=ike" -v "age=27" 'BEGIN{OFS="--";print name,age}'ike--27
复制代码


其余的小技巧;


  • 打印一个文件的行数:awk 'END{print NR}' /etc/passwd

  • 打印最后一行:awk 'END{print $0}' /etc/passwd

  • 打印按指定分隔符分隔的列数:awk -F ":" 'END{print NF}' /etc/passwd

1.8.2、grep

全局搜索的一个正则表达式,并且输出到屏幕上,在文件中对指定的关键词进行查找,并且高亮显示所在行的位置;


参数列表:


  • -i:忽略大小写;

  • -v:取反匹配,即筛选出不满足的行;

  • -n:输出时显示行号;

  • -r:递归查找,一般针对整个文件夹下的内容进行检索时,对应还有个命令 rgrep;


还可以配合正则表达式使用-E


[root@VM-218-88-centos /]# grep -E "(/?)wang" /etc/passwdikejcwang:x:1001:0::/home/ikejcwang:/bin/bashwang:x:1002:1000::/home/wang:/bin/bash[root@VM-218-88-centos /]# grep -E "^wang" /etc/passwdwang:x:1002:1000::/home/wang:/bin/bash
复制代码

1.8.3、sed

作为快速文本的处理利器,应用简单实用广泛;工作流程:读取->执行->显示;


命令格式为:set [options] '编辑命令' file1 file2…


  • -e:使用指定的命令 &脚本来处理输入的文本文件;

  • -f:使用指定的脚本文件来处理输入的文本文件;

  • -n:表示仅显示处理后的结果;

  • -i:直接编辑文本文件;

  • -r,-E:使用扩展正则表达式;

  • -s:将多个文件视为独立文件,而不是单个的长文件流;


常见的操作动作如下:


  • a:增加,在当前行下面增加一行指定内容;

  • c:替换,将选定行替换为指定内容

  • d:删除,删除选定的行;

  • i:插入,在选定行上面插入一行指定内容;

  • p:打印,如果同时指定行,表示打印指定行;如果不指定行,则表示打印出所有内容;如果有非打印字符,则以 ASCII 码输出。其通常与"-n"选项一起使用;

  • s:替换,替换指定字符;

  • y:字符转换。


# 创建一个文件,并输入内容[root@VM-218-88-centos /]# cat <<end >text.txt> haha,1> hehe,2> hihi,3> huhu,4> end# -n(显示执行结果),p:全量打印文件内容[root@VM-218-88-centos /]# sed -n 'p' text.txt haha,1hehe,2hihi,3huhu,4# 只显示第二行[root@VM-218-88-centos /]# sed -n '2p' text.txt hehe,2# 显示第二道第四行的内容[root@VM-218-88-centos /]# sed -n '2,4p' text.txt hehe,2hihi,3huhu,4# 第二个n,表示显示下一行的内容,(输出偶数行)[root@VM-218-88-centos /]# sed -n 'n;p' text.txt hehe,2huhu,4# 输出1-4行之间的奇数行[root@VM-218-88-centos /]# sed -n '1,4{p;n}' text.txt haha,1hihi,3
复制代码


删除的用法,注意:只是删除输出文本,并未删除源文本内容


sed:-e 表达式 #1,字符 3:命令后含有多余的字符[root@VM-218-88-centos ~/ikejcwang]# sed -n "1d;p" text.txt hehe,2hihi,3huhu,4[root@VM-218-88-centos ~/ikejcwang]# sed -n "1,3d;p" text.txt huhu,4
复制代码


替换,/g 全量,/gi 全量且忽略大小写,替换的特殊字符,需要转译(同样支持针对特定行内容替换)


[root@VM-218-88-centos ~/ikejcwang]# sed -n "s/h/ike/;p" text.txt ikeaha,1ikeehe,2ikeihi,3ikeuhu,4[root@VM-218-88-centos ~/ikejcwang]# sed -n "s/h/ike/g;p" text.txt ikeaikea,1ikeeikee,2ikeiikei,3ikeuikeu,4
复制代码


set -i,编辑文本文件,(无需 p 输出打印了);


sed -i 's/https:\/\/真实的域名/http:\/\/9.133.222.55/g' host-templatesed -i 's/真实的域名/9.135.218.88/g' host-templatesed -i 's/真实的签名/KpRklaXpaoTeVTm/g' host-template
复制代码

1.8.4、vim

强大的文本编辑器(值得总结的太多太多……),系统没有的话安装:yum -y install vim*


此处记录的多是常用且复杂的操作:


  • 多行注释:在 ESC 模式下,按 Ctrl+V,滑动选择多行,再按 Shift+i 进入插入模式,输入注释符号,完成后 ESC,加鼠标点一下

  • 多行取消注释:在 ESC 模式下,按 Ctrl+V,滑动选择多行,再按 d 即可完成去注释;

  • 替换模式:正常模式,按 r,然后输入替换字符。(替换一堆,先按 v,进入可视模式选中,然后按 r,输入替换字符);

  • 清空文件:ggdG,(gg:到文件头部,G:到文件尾部);

  • :set spell / nospell:开启/关闭拼写检查功能;


插入模式:


  • gI:在当前行的头部插入;

  • A:在当前行的尾部插入;

  • a:在光标后插入;

  • O:在上面新建一行插入;

  • o:在下面新疆一行插入;

  • :r filename:在当前位置插入指定文件内容;

  • :[n]r filename:在指定行位置插入指定文件内容;


复制粘贴删除:


  • y:复制可视模式下选中的文本;

  • yy 或 Y:复制当前行;

  • y$,y0:从光标当前位置复制到文件尾部,从光标当前位置复制到文件头部;

  • d:删除(剪切)可视模式下选中的文本,没选中就是光标处文本;

  • dd :删除(剪切)1 行(当前行);

  • d$ 或 D:删除(剪切)当前位置到行尾的内容;

  • p:在光标之后粘贴;

  • P:在光标之前粘贴;


替换:


  • :s/old/new/,替换当前行的第一个,加/g 替换当前行的全部


撤回与反撤回:


  • u:撤回,一直到初始打开状态;

  • ctrl+r:反向撤回,一直到最新编辑状态;

1.8.5、wc

word count 的缩写,用于文本内容的统计。单词条目,行数,字符数,字节数……


wc test.txt:执行后显示,第一个是行数,第二个单词数(空格分隔),第三个是字节数。


  • -l:只统计行数;

  • -w:只统计单词数;

  • -c:只统计字节数;

  • -m:只统计字符数;

1.9、进程操作

1.9.1、w

查看当前系统正在登录的用户有哪些(开启的 ssh 连接数量),以及它们各自的休眠时长,行为动作


[root@VM-218-88-centos ~/ikejcwang]# w 17:53:20 up 6 days, 17:29,  4 users,  load average: 0.06, 0.08, 0.08USER     TTY      FROM             LOGIN@   IDLE   JCPU   PCPU WHATroot     pts/0    10.91.79.167     10:15   41:55   0.11s  0.00s -bashroot     pts/1    10.91.79.167     10:15    0.00s  0.02s  0.02s -bashroot     pts/2    10.91.79.167     10:16    6.00s  0.01s  0.01s -bashroot     pts/3    10.91.79.167     10:16    6:49m  0.00s  0.00s -bash
复制代码


  • 17:53:20:当前时间;

  • up 6 days,17:29:系统的正常运行时间(距离上一次重启);

  • 4 users:目前有 4 个 user/from 在线上;

  • load average: 0.06, 0.08, 0.08:系统的平均负载值(统计 3 个时间段),1 分钟为 0.06,5 分钟为 0.08, 15 分钟为 0.08;

  • USER:登录的用户名;

  • TTY:终端名称;

  • FROM:开启 ssh 访问的客户端 IP 地址;

  • LOGIN@:当前会话登录的开始时间;

  • IDLE:会话多久没用活跃(s 秒,m 分钟……);

  • JCPU:当前会话所有进程使用的 CPU 时间,进程结束停止计时;开启新的进程重新计时;

  • PCPU:当前会话的 CPU 执行当前程序花的时间;当前程序即为当前会话的 WHAT 值。

1.9.2、top

动态的显示系统当前资源的利用率和进程运行实况


top,常用参数如下:


  • -p:指定进程号来监控,eg:top -p 6328

  • -i:过滤掉任何闲置或者僵尸进程,eg:top -i

  • -c:显示进程完整的命令;eg:top -c

  • -d:设置动态刷新的时间间隔,eg:每秒刷一次:top -d 1,(默认 3 秒)

  • top -p 320 -p 330 -d 5 -c:间隔 5 秒,完整命令显示进程号 330 和 320 的实时运行情况;


![image-20220811200927949](/Users/wangjinchao/Library/Application Support/typora-user-images/image-20220811200927949.png)


先说交互命令(简单介绍):


  • 1:切换显示每个 cpu 的状态;

  • E:切换内存显示的单位:K,M,G,T,P;

  • M:根据内存占用的大小来进行排序降序;

  • P:根据 CPU 使用的百分比大小进行排序;


然后各项参数配置:


  1. 第一行(系统参数):top:当前时间;up:机器运行时间(距上次重启);user:当前 ssh 会话数;系统负载平均值(1,5,15)分钟

  2. 第二行(当前 task 分类):total:当前有进程数;running:正在运行进程;sleeping:正在休眠进程;stopped:停止进程数;zombie:僵尸进程数;

  3. 第三行(CPU 信息,按 1 展示所有 cpu 信息)

  4. us:用户空间占用 cpu 的百分比(各种脚本,应用,webserver……都算作运行在用户空间的进程);

    sy:内核空间占用 cpu 的百分比(所有进程使用系统资源时都有 Linux 内核处理,当大量 IO 操作,或者 IO 阻塞时,sy 会增大);

    ni:用户进程空间改变过优先级;

    id:空闲 cpu 的百分比;

    wa:等待输入输出占用 cpu 百分比,通过 wa 可以判断系统瓶颈是否在 IO 上面;

    hi:硬中断占用百分比;si:软中断占用百分比;

    st:超分(超卖)的判断指标。如果远大于 0(1、需要额定更多 CPU 资源的虚拟机;2、物理机超卖,多个虚拟机之间在疯狂竞争资源)

  5. 第四行(物理内存信息,按 E 切换换算单位)

  6. total:物理内存总量;

    free:目前空闲内存量;

    used:目前已使用的内存量;

    buffer/cache:目前用作内核缓存的内存量;

  7. 第五行(交换区内存信息,按 E 切换换算单位)

  8. total:交换区内存总量;

    free:空闲交换区内存量;

    used:目前使用的交换区内存量;

    buffer/cache:缓冲的交换区内存量;

  9. 第 4,5 行分别是物理内存与 swap 交互区的信息,所有程序都运行在内存中,但是当内存的 free 变少时不用大惊小怪,有使用就会有释放,并不一定代表物理内存不够用了,而 swap 才是衡量的重要条件,swap 是由硬盘提供支撑的,当物理内存不够使用时,操作系统才会把数据临时放到 swap 中,当 swap 的 used 上升严重,则说明物理内存资源枯竭。

  10. 第六行(进程信息,按 i 过滤调所有闲置 或者僵尸进程)

  11. PID:进程 ID;

    USED:启动该进程的操作用户;

    PR:优先级;

    NI:nice 值,值越小,优先级越高;

    VIRT:进程使用的虚拟内存总量,(按 E 切换换算单位,同下)VIRT=SWAP+RES;

    RES:进程使用的未被换出的物理内存。RES=CODE+DATA;

    SHR:共享内存大小;

    S:进程状态。D=不可中断的睡眠状态,R=运行,S=睡眠,T=跟踪/停止,Z=僵尸进程;

    %CPU:实时更新,上个更新到现在的 CPU 时间占用百分比;

    %MEM:进程使用的物理内存百分比;

    TIME+:进程使用的 CPU 时间总计,单位 1/100 秒;

    COMMAND:命令名/命令行

1.9.3、kill

终止进程的运行,kill [参数] PID


  • -l:不加参数会列出信号全部名称,加参数会显示信号编号,eg:kill -l kill,输出 9;


杀死指定进程:kill -9 PID


高级命令:killall node,杀死所有的同名进程;

1.9.4、nohub

运行指定进程不受终端关闭 &挂断的影响,可以配合 &关键词使用(&:表示将该任务放到后台执行)


nohub node httpServer.js &

1.9.5、ps

静态的列出系统当前运行的进程列表;


  • -aux:显示所有用户的进程(unix 形式);

  • -ef:显示所有用户的进程(Linux 形式);

  • -u:列出当前用户的进程;

  • -aux --sort -pcpu:按 cpu 使用率降序显示;

  • -aux --sort -pmem:按内存使用率降序显示;

1.9.6、systemd

UID        PID  PPID  C STIME TTY          TIME CMDroot         1     0  0 8月05 ?       00:01:57 /usr/lib/systemd/systemd --switched-root --system --deserialize 22
复制代码


系统基础服务组件的集合,PID 为 1,负责启动其他程序(服务),可在/etc/systemd/system/查看并新建 &编辑服务,然后systemctl daemon-reload,然后启动 &重启指定服务;


命令格式:systemctl [command] [serviceName]


  • reload:重新加载服务配置文件;

  • enable:设置服务开机自启;

  • disable:设置服务开机不自启;

  • Is-enabled:查看服务是否开机自启;

  • systemctl list-units:列出正在运行的 units,eg:systemctl list-units |grep wukong (筛选所有 wukong 服务)

  • systemctl -a:列出所有服务,eg:systemctl -a | grep wukong |grep dead(查看死掉的 wukong 服务)

1.10、文件操作

1.10.1、tar

压缩打包工具,正常流程是:先使用 tar 将多个文件归档为一个总文件(archive),然后再用 gzip 将 archive 压缩成更小的文件,但是日常很多操作都是一步到位;


  • -xvf:(x 解开,x 细节展示,f 文件)解压缩,-C:解压缩到指定目录;

  • -tf:显示归档文件的内容,不解开;

  • -cvf:(c 创建,x 细节展示,f 文件)打包,

  • -z:归档+压缩;解压 gz 格式的压缩文件(省略了 gzip,gunzip,一步到位)


tar -cvf file.tar file/:将 file 文件夹打包归档成 file.tar,并展示归档细节


tar -xvf file.tar -C file_new:将 file.tar 解压缩至 file_new 目录中;


如果压缩包本身就为 gz 格式


tar -zcvf file.tar.gz file/:将 file 文件夹打包归档成 file.tar.gz,并展示归档细节


tar -zxvf file.tar.gz -C file_new:将 file.tar.gz 解压缩至 file_new 目录中;


(日常多为-z 使用,但并没有标注压缩文件后缀.gz,可以使用 file 命令查看)


少见的.tar.xz 格式:


tar -Jcvf name.tar.xz ./:压缩,tar -Jxvf name.tar.xz :解压

1.10.2、zip/unzip

发布于: 刚刚阅读数: 3
用户头像

晴天

关注

还未添加个人签名 2020.08.21 加入

全栈程序员

评论

发布
暂无评论
shell养成计划之易筋经篇(持续更新)_Linux_晴天_InfoQ写作社区