什么是Shell

解释Shell脚本名词之前,我们先来说下什么是Shell?

Shell是一个命令解释器,它在操作系统的最底层,负责直接与用户对话,把用户的输入解释给操作系统,并处理各种各样的操作系统的输出结果,输出到屏幕返回给用户。这种对话方式可以是交互的方式(从键盘输入命令,可以立即得到shell的回应),或非交互(脚本)的方式。

命令行解释器:使用户得以与内核进行沟通的“翻译官”

下面图中黄色部分就是命令解释器shell。

提示:Shell在英文中的意思是贝壳,从上图我们可以看出,命令解释器shell就像一个贝壳一样包住了系统核心。

解释:

用户下达指令,shell把用户的指令翻译成`系统内核`能识别的二进制数,然后传达给系统内核,系统内核会把指令进行查看分析,然后下达“进程调度”和“资源分配”指令给CPU,让CPU去执行,然后由计算机硬件来显示结果。

什么是shell脚本

Linux  Shell脚本 :实现某种功能的,有执行权限的文本文件

内核的作用:资源分配和进程调度

命令或语句不在命令行执行,而是通过一个程序文件执行时,该程序就被称为shell脚本或Shell程序,shell程序很类似DOS系统下的批处理程序(*.bat)。用户可以在shell脚本中敲入一系列的命令或命令语句。这些命令、变量和流程控制语句等有机的结合起来就形成了一个功能强大的shell脚本。

Windows下利用批处理程序bat开发的备份网站及数据库的脚本

@echo off
set date=%date:~,%-%date:~,%-%date:~,%
mysqldump -uroot -poldboy -A -B > D:\bak\"%date%".sql
rar.exe a -k -r -s -m1 D:\bak\"%date%".sql.rar D:\bak\"%date%".sql
del D:\bak\*.sql
rar.exe a -k -r -s -m1 D:\bak\"%date%"htdocs.rar D:\work\PHPnow\htdocs

范例1:清除.var/log下messages日志文件的简单命令脚本

#把所有命令放在一个文件里堆积起来就形成了脚本,下面就是一个最简单的命令堆积形成的shell脚本。

#必须使用root身份来运行这个脚本

#清除日志脚本,版本1

cd /var/log
cat /dev/null > messages
echo "Logs cleaned up."
#提示:/var/log/messages是系统的日志文件

看完这个脚本有什么想法?

)不是root执行不了

)没有流程控制,就是没有逻辑性

范例2:包含命令、变量和流程控制语句的清除/var/log下messages日志文件的shell脚本

#!/bin/bash
#清除日志脚本,版本2
LOG_DIR=/var/log
ROOT_UID= #$UID=0的时候,用户才具有root用户的权限
#要使用root用户来运行.
if [ "$UID" -ne "$ROOT_UID" ]
then
echo "Must be root to run this scripts."
exit
fi
cd $LOG_DIR || {
echo"Cannot change to necessary directory." >&
exit
} cat /dev/null > messages && echo "Logs cleaned up."
exit
#退出之前返回0表示成功,返回1表示失败

扩展:

清除日志的三种方法:

[root@Web ~]# echo >test.log
[root@Web ~]# >test.log
[root@Web ~]# cat /dev/null >test.log

应用场景:保留文件,清空内容

脚本在执行时会启动一个子shell进程;

1.命令行中启动的脚本会继承当前shell环境变量;

2.系统自动执行的脚本(非命令行启动)就需要自我定义需要各环境变量;

编写脚本

1.指定脚本的执行环境  #!/bin/bash

2.注释信息

3.脚本的功能体

进程和shell的关系

1.在每个进程看来,当前主机上只存在内核和当前进程,不知道别的进程存在

2.进程是程序的副本,进程是程序执行实例

3.进程可同名,进程号不同就是不同的进程

4.进程是程序的副本,进程是程序执行示例

5.多个用户同时登录shell,每个Shell都会有所不同,彼此之间各不相干

6.允许同一个用户登录多次,每个Shell都会有所不同,彼此之间各不相干

7.同一个用户在不同地方登录的Shell都会不同,都对应不同的Shell进程
8.bash自身是一个外部程序,但启动以后会带有内部命令
9.父Shell的设定对于子Shell是无效的,所之亦然。
10.shell之间可以交互打开

shell脚本与perl,php,python语言的差别?

Shell的优势在于处理操作系统底层的业务(大量的命令为它做支撑,例如,grep,sed,awk)。

一键安装,报警脚本,常规的业务应用,shell开发更简单快速。

php,python优势在于开发运维工具,web界面的管理工具

Shell脚本很擅长处理纯文本类型的数据,而linux中几乎所有的配置文件、日志文件(如nfs,rsync,httpd,nginx,lvs等)都是纯文本类型的文本。因此,如果学好Shell脚本语言,就可以利用它Linux系统中发挥巨大的作用。

Linux系统支持的Shell

类型                说明
bsh:Bourne Shell     70年代中期诞生于贝尔实验室,脚本编程功能较强
csh             80年代早期诞生于加利福尼亚大学,使用C语言风格,命令行交互方便
ksh:Korn Shell     兼容Bsh的语法和C语法的交互特性
bash:Bourne-Again Shell bsh的升级版,吸取了ksh的一些特点,是大多数Linux的默认Shell程序 zsh             兼备各种Shell程序的优点,交互式操作效率更高

Shell脚本语言是弱类型语言,较为通用的shell有标准的Bourne shell (sh)和 C shell (csh)。其中 Bourne shell (sh)。其中 Bourne shell (sh)已经被bash shell取代。

当前的Linux主机支持哪些Shell?

#cat /etc/shells
/bin/sh //多数Unix默认的Shell
/bin/bash //多数Linux默认使用的Shell
/sbin/nologin //非登录Shell
/bin/tcsh
/bin/csh
/bin/csh
在RHEL系统中,实际上sh是bash的符号链接

CentOS Linux系统默认的shell是():

[root@Web ~]# echo $SHELL
/bin/bash
[root@Web ~]# grep root /etc/passwd
[root@Web ~]# grep root /etc/passwd
root:x:::root:/root:/bin/bash

Bash的基本特性

Tab键补全、快捷键
命令历史
命令别名
标准输入输出
重定向
管道操作

Tab键补全

命令补全    搜索PATH环境变量所指定的每个路径下以我们给出的字符串 开头的可执行文件,如果多于一个,两次tab,可以给出列表;否则将直接补全;
路径补全 搜索我们给出的起始路径下的每个文件名,并试图补全

快捷键

快捷键    注释
Ctrl+a 跳到命令行首
Ctrl+e 跳到命令行尾
Ctrl+u 删除光标至命令行首的内容
Ctrl+k 删除光标至命令行尾的内容
Ctrl+l 清屏

命令历史

默认记录1000条最近执行过的命令

存放位置:~/.bash_history

环境变量    注释
PATH   命令搜索路径
HISTSIZE 命令历史缓冲区大小

命令历史:history

参数选项    注释
-c 清空命令历史
-d OFFSET [n] 删除指定位置的命令
-w 保存命令历史至历史文件中

命令历史的使用技巧:

参数选项    注释
!n    执行命令历史中的第n条命令
!-n   执行命令历史中的倒数第n条命令;
!!    执行上一条命令;
!string 执行命令历史中最近一个以指定字符串开头的命令
!$    引用前一个命令的最后一个参数
Esc, .
Alt+.

命令别名

语法:

alias CMDALIAS='COMMAND [options] [arguments]'

有效范围

在shell中定义的别名仅在当前shell生命周期中有效
别名的有效范围 仅为当前shell进程

相关操作

相关操作                注释
aliase           列出已定义的命令别名
unaliase 别名        删除指定的命令别名
unaliase -a        清空所有别名
alias 别名='实际命令'   定义新的命令别名

如何让定义的别名命令生效?

vim  ~/.bashrc    只对某个用户生效
vim /etc/bashrc 对所有用户生效

标准输入输出

1.标准输入:从该设备接收用户输入的数据

2.标准输出:从该设备向用户输出的数据

3.标准错误:通过该设备报告执行中的出错信息

类型      设备文件      文件描述号    默认设备
标准输入 /dev/stdin         键盘
标准输出 /dev/stdout         显示器
标准错误 /dev/stderr        显示器

重定向

重定向:改变标准输入/输出/错误输出的方向

set -C    禁止对已经存在文件使用覆盖重定向
    强制覆盖输出,则使用 >|
set +C 关闭上述功能

类型

类型                    操作符          用途
重定向输入                <      将文本输入来源由键盘改为指定的文件
重定向输出                >     将命令行的正常执行输出保存到文件,而不是直接显示在屏幕上
                   >>     与>类似,但操作是追加而不是覆盖
重定向错误               >     将命令行的执行错误信息保存到文件,而不是直接显示在屏幕上
                   >> 与2>类似,但操作是追加而不是覆盖
混合重定向(重定向正确和错误输出信息) &>    相当于>和2>,覆盖到同一个文件
                   &>>   相当于>和2>>,追加到同一个文件

管道

管道:前一个命令的输出,作为后一个命令的输入

管道操作符”|“
cmd1 | cmd2 [...|cmdn] 将cmd1的输出结果,作为cmd2的输入

例如:

#pgrep -l "." | wc -l————统计运行的进程数
#ifconfig | grep "HWaddr"————查看本机的MAC地址信息

shell脚本的建立和执行

shell脚本(bash shell程序)通常是在编辑器(如vi/vim)中编写,由Unix/Linux命令、bash shell命令、程序结构控制语句和注释等内容组成。

脚本开头(第一行)

一个规范的shell脚本第一行会指出由哪个程序(解释器)来执行脚本中的内容,在linux bash编程中一般为:

#!/bin/bash

#!/bin/sh

“#!”又称为幻数,在执行bash脚本的时候,内核会根据它来确定该用哪个程序来解释脚本中的内容。这一行必须在脚本顶端的第一行,如果不是则为注释。

sh和bash的区别:

[root@Web ~]# ls -l /bin/sh
lrwxrwxrwx. root root 9月 /bin/sh -> bash
[root@Web ~]# ll /bin/sh
lrwxrwxrwx. root root 9月 /bin/sh -> bash

提示:sh为bash的软链接,这里推荐用标准写法#!/bin/bash

下面是linux常用脚本语言开头的编码写法,不同语言脚本的开头一般都要加上如相应语言的开头标识内容

#!/bin/sh
#!/bin/bash
#!/usr/bin/awk
#!/bin/sed
#!/usr/bin/tcl
#!/usr/bin/expect
#!/usr/bin/perl
#!/usr/bin/env python

Centos和RedHat Linux下默认的Shell均为bash。因此,在写shell脚本的时候,我们的脚本的开头也可以不加#!/bin/bash。但如果当前的shell非你默认的shell时,比如tcsh,那么就必须要写#!了。否则脚本文件就只能执行命令的集合,不能够使用shell内建的指令了,建议读者养成习惯,不管什么脚本最好都加上开头语言标识。

如果脚本的开头不指定解释器,那么,就要用对应的解释器来执行脚本。例如:

bash test.sh
python test.py

脚本注释

在shell脚本中,跟在(#)井号后面的内容表示注释,用来对脚本进行注释说明,注释部分不会被当作程序执行,仅仅是给人看的,系统解释器看不到的,注释可自成一行,也可以跟在脚本命令后面与命令在同一行。开发脚步时,如果没有注释,其他人就很难理解脚本究竟在做什么,时间长了自己也会忘记。因此,我们要尽量养成对所做的工作(脚本等)书写注释的习惯,不光是方便别人,也方便自己,否则,写完一个脚本后也许几天后就记不起脚本的用途了,再重新阅读也会浪费很多宝贵时间。对于团队的协作也不利。

Shell脚本的执行

当shell脚本以非交互式的方式运行时,它会先查找环境变量ENV,该变量指定了一个环境文件(通常是.bashrc),然后从该环境变量文件开始执行,当读取了ENV文件后,SHELL才开始执行shell脚本中的内容。

Shell脚本的执行通常可以采用一下三种方式:

bash script-name 或sh script-name(推荐使用)
path/script-name或./script-name(当前路径下执行脚本)
source script-name或. script-name #注意”.”点号

执行说明:

1.第一种方法是当脚本文件本身没有可执行权限(即文件x位为-号)时常使用的方法,这里推荐使用bash执行,或者文件开头没有指定解释器(推荐的方法)

2.第二种方法需要先将脚本文件的权限改成可执行文件(即文件加x位),具体方法:chmod u+x script-name或chmod 755 script-name。

然后通过脚本路径就可以直接执行脚本了。

在生产环境中,不少读者在写完shell脚本后,由于疏忽忘记给予该脚本文件执行权限,就直接应用了,结果导致脚本没有按自己的意愿手动或定时执行。

避免的方法是用第一种方法替代第二种。

3.第三种方法是使用source或者”.”点号读入或加载指定的shell脚本文件(如san.sh),然后依次执行指定shell脚本文件san.sh中的所有语句。这些语句将作为当前父shell脚本father.sh进程的一部分运行。因此,使用source或者”.”点号可以将san.sh自身脚本中的变量的值或函数等的返回值传递到当前的父shell脚本father.sh中使用。这是第三种方法和前两种的最大区别。也是值得读者注意的地方。

Source或者'.'点号命令的功能是在当前shell中执行source或者'.'点号加载并执行的相关脚本文件中的命令及语句,而不是产生一个子shell来执行命令文件中的命令

下面我们举例说明

[zgy@Web ~]$ cat >test.sh                   #编辑test.sh脚本文件

echo 'I am zgy' echo 'I am zgy'  

输入"echo 'I am oldboy'"内容后按回车,然后在按ctrl+d组合键即可结束编辑。此操作作为特殊编辑方法,作为cat用法的扩展提及(在使用中去记忆是个好习惯)。

[zgy@Web ~]$ cat test.sh  

echo 'I am zgy'   

[zgy@Web ~]$ sh test.sh         #使用第一种方式的sh命令执行test.sh脚本文件

I am zgy

[zgy@Web ~]$ bash test.sh      #使用第一种方式的bash命令执行test.sh脚本命令

I am zgy

我们使用第一种方法,发现均可以执行并得到预期的结果。

zgy@Web ~]$ ls -l test.sh
-rw-rw-r--. zgy zgy 4月 : test.sh [zgy@Web ~]$ ./test.sh #使用第二种方式"./"在当前目录下执行test.sh脚本文件,可以发现,这个地方无法自动补全。
-bash: ./test.sh: 权限不够 #提示:此处没有可执行权限

但是可以用source或者"."点号执行。

[zgy@Web ~]$ . test.sh
I am zgy
[zgy@Web ~]$ source test.sh
I am zgy

提示:"."点号和source命令的功能相同,都是读入脚本并可以执行脚本

给test.sh加执行权限

[zgy@Web ~]$ chmod u+x test.sh
[zgy@Web ~]$ ./test.sh
I am zgy

可以看到,给test.sh加完可执行权限就可以执行了。

现在测试第三种source或者"."点号的特殊的传递变量值到当前shell的例子

[zgy@Web ~]$ echo 'userdir=`pwd`'>testsource.sh  #行的内容通常用echo很方便。
[zgy@Web ~]$ cat testsource.sh
userdir=`pwd`
[zgy@Web ~]$ sh testsource.sh
[zgy@Web ~]$ echo $userdir

#此处为空,并没有出现当前路径输出,这是为什么呢?

根据上面例子,可以发现,通过sh或bash命令执行过的脚本,脚本结束后在当前shell窗口查看userdir变量的值,发现变量值是空的。现在以同样的步骤改用source执行,然后再看看userdir变量的值

[zgy@Web ~]$ source testsource.sh
[zgy@Web ~]$ echo $userdir
/home/zgy

再看看系统Nfs服务的脚本如何使用”.”号的。

# Source function library.
. /etc/rc.d/init.d/functions

提示:操作系统及服务自带的脚本是学习的标杆和参考(虽然有时感觉不是很规范)

结论:

通过source或”.”点号加载执行过的脚本,在脚本结束后脚本中的变量值(包括函数)在当前Shell中依然存在,而是sh和bash则不行。

因此,在做Shell脚本开发时,如果脚本中有需求引用其他脚本的内容或者配置文件时,最好用”.”点号或source在脚本开头加载该脚本或配置文件,

然后再下面的内容用可以调用source加载的脚本及文件中的变量及函数等内容

某互联网公司Linux运维职位实际面试笔试

、已知如下命令返回结果,请问echo $user的返回的结果为()
[zgy@Web ~]$ cat test.sh
user=`whoami`
[zgy@Web ~]$ sh test.sh
[zgy@Web ~]$ echo $user
问:执行echo $user命令的结果是什么?
)当前用户
)zgy
)空(无内容输出) #这个是正确答案

Shell脚本开发基本规范及习惯

1)开头指定脚本解释器

#!/bin/sh或#!/bin/bash

2)开头加版权版本等信息

#Date: : --

#Author Created by zgy

#Mail @qq.com

#Function:  This scripts function is...

#Version 1.1

3)脚本中不用中文注释

尽量用英文注释,防止本机或切换系统环境后中文乱码的困扰

4)脚本以.sh为扩展名

例:script-name.sh

5)代码书写优秀习惯

1.成对内容的一次写出来,防止遗漏。如:

[]、{}、''、``、""

2.[]中括号两段要有空格,书写时即可留出空格[  ],然后在退格书写内容。

3.流程控制语句一次书写成,再添加内容,如:

if语句格式一次完成:

if  条件内容
then
内容
fi

for语句格式一次完成:

for
do
内容
done

提示:while和util,case等语句也是一样

6)通过缩进让代码易读

if 条件内容
then
内容
fi

提示:好的习惯可以避免很多不必要的麻烦,提升很多的工作效率。

一、Shell概述的更多相关文章

  1. shell概述与echo命令

    一.Shell概述 1.什么是shell? 由此可见shell是用户与系统进行交互的接口,通过执行各种命令来完成时间处理与调度. 2.shell分类 Shell类别 易学性 可移植性 编辑性 快捷性 ...

  2. Shell概述1

    Shell概述1 脚本文件内容(vim ex2) #!/bin/bash #If no arguments,then listing the current directory. #Otherwise ...

  3. Shell概述

    一,Shell原理

  4. Linux系列教程(二十)——Linux的shell概述以及如何执行脚本

    从这篇博客开始,我们将进入Linux的shell脚本的学习,这对于Linux学习爱好者而言是特别重要的一节,也是特别有意思的一节,shell 脚本就像我们知道的Java,php类似的编程语言一样,通过 ...

  5. HoloLens开发手记 - HoloLens shell概述 HoloLens shell overview

    使用HoloLens时,shell是由你周围的世界和来自系统的全息图像构成.我们将这种空间成为混合世界(mixed world). shell包含了一个可以让你将全息图像和应用放置在世界中的开始菜单( ...

  6. 【第一章】Shell 概述

    一.什么是Shell? shell是一个命令解释器,它不仅包含大量的命令以实现操作系统的对话,还可以实现定义变量.条件判断.循环控制.函数调用等功能. 作用:解释执行用户输入的命令及程序等. 从键盘输 ...

  7. Shell 概述、截取字符操作等

    Shell 是用C语言编写的程序,便于用户与Linux内核系统进行交互. Linux的Shell种类众多,常见的有: Bourne Again Shell (/bin/bash) Bourne She ...

  8. Linux学习笔记 (八)Shell概述

    一.什么是Shell? Shell是一个命令行解释器,它为用户提供了一个向Linux内核发送请求以便运行程序的界面系统级程序,用户可以用Shell来启动,挂起,停止甚至是编写一些程序.Shell还是一 ...

  9. hbase shell概述

    hbase shell-general(常规指令):http://www.cnblogs.com/husky/p/6374867.html hbase shell-ddl(表定义指令):http:// ...

  10. Shell 01 shell概述

    1.查看shells:/etc/shells /bin/sh /bin/bash /sbin/nologin /usr/bin/sh /usr/bin/bash /usr/sbin/nologin / ...

随机推荐

  1. 【题解】P4841 城市规划(指数型母函数+多项式Ln)

    [题解]P4841 城市规划 P4841 城市规划 超级弱化版本(DP):POJ - 1737 两张图不同当且仅当边的分布不一样的时候,带编号最后乘一个阶乘即可,现在最主要的问题就是"联通& ...

  2. 「Vijos 1283」「OIBH杯NOIP2006第二次模拟赛」佳佳的魔杖

    佳佳的魔杖 背景 配制成功了珍贵的0号药水,MM的病治好了.轻松下来的佳佳意外的得到了一个好东西--那就是--一种非常珍贵的树枝.这些树枝可以用来做优质的魔杖!当然了,不能只做自己的,至少还要考虑到M ...

  3. AnyDesk免费远程工具

    AnyDesk是一款声称速度最快的免费长途衔接/长途桌面操控软件,是前TeamViewer开发小组人员自立门户的商品,它拥有领先的视频压缩技能DeskRT,能够轻松穿透防火墙/路由器,实测在电信.移动 ...

  4. CF854C Planning优先队列|set

    C. Planning 传送门 Helen works in Metropolis airport. She is responsible for creating a departure sched ...

  5. Vim区块选择

    区块选择的按键意义: 区块选择的按键意义 v 字符选择,光标经过的地方反白 V 列选择,光标经过的列反白 [ctrl]+v 区块选择,可以用长方形的方式选择资料 d 将发白的地方删除掉 y 将反白的地 ...

  6. MVC 统一验证Token demo

    /// <summary> /// 获取token /// </summary> /// <param name="staffId"></ ...

  7. python二维列表求解所有元素之和

    2020-01-14 相信很多初学小伙伴都会遇到二维列表求解所有元素之和问题,下面给出两种两种常见的求和方法. 方法1: 思想:遍历整个二维列表元素,然后将所有元素加起来 def Sum_matrix ...

  8. 关于java php go 中AES加解密秘钥长度问题

    今天心血来朝,想用go把php中的一个小功能重写一下,但在解密aes加密的数据时碰到了个坑! php的mcrypt拓展(貌似php7.1版本以上不支持了)提供了aes的加解密: 而且php aes 的 ...

  9. Webpack实战(二):webpack-dev-server的介绍与用法

    为什么要用webpack-dev-server 在开发中,我们都可以发现仅仅使用Webpack以及它的命令行工具来进行开发调试的效率并不高,每次编写好代码之后,我们需要执行npm run build命 ...

  10. Eclipse常用快捷键【转】

    Eclipse的编辑功能非常强大,掌握了Eclipse快捷键功能,能够大大提高开发效率.Eclipse中有如下一些和编辑相关的快捷键.1. [ALT+/]此快捷键为用户编辑的好帮手,能为用户提供内容的 ...