Shell编程
1.为什么学习shell编程
1.1 什么是shell
shell的作用:
- 解释执行用户输入的命令或程序等.
- 用户输入一条命令,shell就解释一条.
- 键盘输入命令,Linux给予响应的的方式,成为
响应式
.
- shell是一块包裹着系统核心的壳,处于操作系统的最外层,与用户直接对话,把用户的输入,解释给操作系统,然后处理操作系统的输出结果,输出到屏幕给用户看到结果.
- 从我们登录Linux,输入账号密码进入到Linux交互式界面,所有的操作,都是交给shell解释并执行.
- 我们想要获取计算机的数据,不可能每次都编写程序,编译后,再运行,再得到我们想要的,例如你想找到一个文件,可以先写一段C语言的代码,然后调用系统函数,通过gcc编译后,运行程序才能找到文件…
- 因此有大牛开发出了shell解释器,能够让我们方便的使用Linux,例如只能敲下
ls -lh
这样的字符串,shell解释器就会针对这句话解释,解释成ls -l -h
,然后执行,通过终端输出结果,无论是图形化或者是命令行界面.
既然我们用的图形化界面,区别也就是:
- 命令行操作,shell解释后,输出结果到黑屏命令行界面.
- 图形化操作,shell接受点击动作,输出图形数据.
当命令或者程序语句写在文件中,我们执行文件,读取其中的代码,这个程序文件就称之为shell脚本.
在shell脚本里定义多条Linux命令以及循环控制语句,然后将这些Linux命令一次性执行完毕,执行脚本文件的方式称之为非交互式方式
.
- windows中存在
*.bat
批处理及哦啊吧.- Linux中长虹
*.sh
脚本文件.
shell脚本的规则
- 在Linux系统中,shell脚本称之为(bash shell程序)通常都是vim编辑,由Linux命令,bash shell指令,逻辑控制语句和注释信息组成.
1.2 Shebang
计算机程序中,
Shebang
指的是出现在文本文件的第一行前两个字符#!
.
在Unix系统中,程序会分析shebang
后面的内容,作为解释器的指令,例如:
以#!/bin/sh
开头的文件,程序在执行的时候回调用/bin/sh
,也就是bash解释器.- 以
#!/usr/bin/python
开头的文件,代表指定python解释器取执行.- 以
#!/usr/bin/env
解释器名称,是一种在不同平台都能正确找到解释器的办法.
注意事项:
- 如果脚本未指定
shebang
,脚本执行的时候,默认用当前的shell取解释脚本,即$SHELL
.- 如果
shebang
指定了可执行的解释器,如/bin/bash, /usr/bin/python
,脚本在执行时,文件名作为参数传递给解释器.- 如果
#!
执行的解释器没有可执行的权限,则会报错bad interpreter:Permission denied
.- 如果
#!
指定的解释程序不是一个可执行的文件,name指定的解释器会被忽略,转而交给当前的SHELL去执行这个脚本.- 如果
#!
指定的解释器不存在,那么会报错bad interpreter:No such file ro directory
.#!
之后的解释程序,需要写其绝对路径(如:#!/bin/bash),它是不会自动到$PATH中寻找解释器的.- 如果你使用
bash test.sh
这样的命令来执行脚本,那么#!这一行将会被忽略掉,解释器当然是用命令中显示指定的bash.
脚本示例:
1.3 脚本注释
- 在shell脚本中,
#
后面的内容代表注释掉的内容,提供给开发者或者使用者观看,系统会忽略此行.- 注释可以单独写一行,也可以跟在命令后面.
- 尽量保持爱写注释的习惯,便于以后回顾代码的含义,尽量使用英文,而非中文.
1.4 执行shell脚本的方式
bash test.sh
或者sh test.sh
,文件本身没权限执行,没x(执行)权限,则使用此方法,或脚本未指定shebang
,重点推荐此方法.- 使用
绝对/相对
路径执行脚本,需要文件含有x权限.source test.sh
或者. test.sh
,代表执行的含义,source等于点.
.- 少见的用法,
sh < test.sh
.
shell脚本语言属于一种弱类型语言,
无需声明变量类型,直接定义使用
.
强类型语言,必须先定义变量类型,确定是数字,字符串等,之后再赋值同类型的值.
centos7系统中支持的shell情况,有如下种类:
默认的sh解释器:
1.5 shell的优势
虽然有诸多脚本编程语言,但是对于Linux操作系统内部应用而言,shell是最好的工具,Linux底层命令都支持shell,以及结婚三剑客(grep,sed,awk)进行高级语法.
- 擅长系统管理脚本开发,如软件启停脚本,监控报警脚本,日志分析脚本.
Linux默认shell
2 Bash基础特性
2.1 bash是什么
- bash是一个命令处理器,运行在文本窗口中,并能执行用户直接输入的命令.
- bash还能从文件中读取linux命令,称之为脚本.
- bash支持通配符,管道,命令替换,条件判断等逻辑控制语句.
2.2 历史命令
Shell会保留其会话中用户提交执行的命令
history #命令,查看历史命令记录,注意[包括文件中内存中的历史记录]
history #以及参数
-c:清空内存中命令历史.
-r: 从文件中回复历史命令.
数字 : 显示最近n条命令 history 10
[chentf_vm@localhost ~]$ echo $HISTSIZE #SHELL进程可以保留的历史的条数
1000
[chentf_vm@localhost ~]$ echo $HISTFILE #存放历史命令文件,用户退出登录,持久化命令个数
/home/chentf_vm/.bash_history
[chentf_vm@localhost ~]$ !187 # ! id调用历史命令 !! 执行上次的命令
2.3 变量含义
变量是暂时存储数据的地方,是一种数据标记(房间号,标记了客人所在的位置),数据存储在内容空间,通过调用正确的变量,即可取出对应的值.
2.4 shell变量
- 变量定义与赋值,注意变量与值之间不得有空格
name=“张三”
变量名,变量类型,bash默认把所有的变量都认为是字符串
bash变量是弱类型
,无需事先声明类型,是将声明和赋值同时进行的.
- 变量替换/引用
[root@localhost ~]# name="张三"
[root@localhost ~]# echo ${name}
张三
[root@localhost ~]# echo $name #可以省略花括号
张三
- 变量名定义规则
- 名称定义要做到见名知意,按照规则来,且不得用保留关键字(help命令检查保留关键字)
- 只能包含数字,字母,下划线
- 不能以数字开头
- 不能用标点符号
- 变量表严格区分大小写
有效的变量名:
NAME_ZHANGSAN
_zhangsan
zhangsan1
zhangSan1
zhang_san
无效的变量名:
?zhangsan
zhang*san
zhang+san
2.5 变量的作用域
本地变量
:`只针对当前的shell进程
pstree检查进程树
[root@localhost ~]#
[root@localhost ~]# name=123
[root@localhost ~]# echo %name
123
[root@localhost ~]# csh #切换shell,变量丢失
[chentf_vm@localhost ~]# echo $name
name: Undefined variable.
环境变量:
也称为全局变量,针对当前shell以及任意子进程,环境变量也芬自定义,内置两种环境变量.局部变量:
针对在shell函数或者是shell脚本中定义的.位置变量参数:
用于shell脚本中传递参数.特殊变量:
shell内置的特殊功效变量
$? #常用在脚本中判断上一行的命令是否执行成功
- 0:成功
- 1-255:错误码
- 自定义变量
变量赋值: varName=value
变量引用: v a r N a m e , {varName}, varName,varName
双引号,变量名会替换成变量值
单引号,识别为普通的变量值
[root@localhost ~]# n1=1
[root@localhost ~]# n2=2
[root@localhost ~]# n3="$n1"
[root@localhost ~]# echo $n3
1
[root@localhost ~]# n4='$n2'
[root@localhost ~]# echo $n4
$n2
- 不同的shell执行方式,不同的shell环境
- 每次调用bash/sh解释器执行脚本,都会开启一个子shell,因此不保留当前的shell变量,通过
pstree
命令检查进程树- 调用source或者点
.
符号,在当前shell环境加载脚本,因此保留变量
#演示
1.开启子shell的执行方式
[root@localhost ~]# cat make_vars.sh
name="张三"
[root@localhost ~]# echo $name
李四
[root@localhost ~]# bash make_vars.sh
[root@localhost ~]# echo $name
李四
2.不开启子shell的执行方式
[root@localhost ~]# source make_vars.sh
[root@localhost ~]# echo $name
张三
- linux中``反引号
在linux中反引号中的命令执行结果会被保留
[root@localhost ~]# echo $name
ls
[root@localhost ~]# name=`ls`
[root@localhost ~]# echo $name
anaconda-ks.cfg initial-setup-ks.cfg kibana-6.8.0-x86_64.rpm
[root@localhost ~]# ls
anaconda-ks.cfg initial-setup-ks.cfg kibana-6.8.0-x86_64.rpm
2.6 环境变量设置
环境变量一般指的是用export内置命令导出的变量,用于定义shell的运行环境,保证shell命令的正确执行.
shell通过环境变量确定登录的用户名,PATH路径,文件系统等各种应用.
环境变量可以在命令行中临时创建,但是用户退出shell终端,变量即丢失,如果要永久生效,需要修改环境变量配置文件
- 用户个人配置文件:
~/.bash_profile, ~/.bashrc
远程登录用户特有文件,每个用户都有自己的环境变量配置文件,~/.bas_profile, ~/.bashrc
,且以个人配置文件,优先加载变量,读取,以个人的优先生效.- 全局配置文件
/etc/profile, /etc/bashrc
,且系统建议最好创建在/etc/profile.d/
,而非直接修改主文件,修改全局配置文件,影响所有登录系统的用户
检查系统环境命令的命令
- set: 输出所有变量,包括全局变量,局部变量
[chentf_vm@localhost ~]# set | wc -l #统计所有变量
36
[chentf_vm@localhost ~]# set | grep ^path #找出以path开头的所有变量
path (/usr/local/bin /usr/bin /usr/local/sbin /usr/sbin /home/chentf_vm/.local/bin /home/chentf_vm/bin)- env: 只显示全局变量
- declare: 输出所有的变量,如同set
- export: 显示和设置环境变量值
撤销环境变量
- unset 变量名: 删除变量或者函数
设置只读变量
- readonly: 只要有shell结束,只读变量失效
系统保留环境变量关键字
bash内嵌了诸多环境变量,用于定义bash的工作换
[chentf_vm@localhost ~]# export | awk -F '[:=]' '{print $3}' #过滤出,格式化所有linux环境变量名字
bash*多命令执行
[chentf_vm@localhost ~]# ls /data/;cd /tmp/;cd /home;cd /data