文章目录
shell编程基础
现在我们使用的操作系统(Windows、Mac os、Android、IOS等)都是带图形化界面的,简单直观,容易上手,对专业用户(程序员、工程师等)和普通用户都非常适用;计算机离不开图形界面。
然而现在计算机的早期并没有图形界面,我们只能通过一个一个的命令来控制计算机,这些命令有成百上千个之多,且不说记住这些命令非常困难,每天面对没有任何色彩的“黑屏”本身就是一件枯燥的事情;这个时代的计算机还远远谈不上炫酷和普及,只有专业人员才能使用
编程语言的分类
根据运行方式:
编译运行:源代码 --> 编译器 --> 二进制文件(程序文件)
解释运行:源代码 --> 运行时启动解释器,由解释器边解释边运行
根据其编程过程中功能的实现是调用库还是调用外部的程序文件:
shell脚本编程:利用系统上的命令及编程组件进行编程
完整编程:利用库或编程组件进行编程
编程模型:过程式编程语言,面向对象的编程语言
程序:指令+程序
过程式编程语言:以指令为中心来组织代码,数据是服务于代码
顺序执行
选择执行
循环执行
代表:c,bash,Python
对象式编程:以数据为中心来组织代码,围绕数据来组织指令
类(class):实例化成为对象,method
代表:Java,c++,Python
如何编写shell脚本
几乎所有编程语言的教程都是从著名的“Hello World”开始的,出于这种传统的尊重(或者说落入俗套),我们第一个脚本也输出“Hello World”。
打开文本编辑器,新建一个文本文件,命名为test.sh
在test.sh中输入代码:
#!/bin/bash
echo "Hello World" #这是一条语句
第1行的 #! 是一个约定的标记,它告诉系统这个脚本需要什么解释器来执行,即使用哪种shell;后面的 /bin/bash 就是指明了解释器的具体位置
第2行的 # 及其后面的内容是注释。shell脚本中所有以 # 开头的都是注释(当然以 #! 开头的除外)。写脚本的时候,多写注释是非常有必要的,以方便其他人能看懂你的脚本,也方便后期自己维护时看懂自己的脚本----实际上,即便是自己写的脚本,在经过一段时间后也很容易忘记。
下面写出了一段稍微复杂的shell脚本:
#!/bin/bash
# Copyright (c)http://c.biancheng.net/shell/
echo "What is your name?"
read NAME
echo "Hello,$NAME"
在第4行中表示终端读取用户输入的数据,并将数据赋值给NAME变量。read命令用来从标准输入文件(standard input,stdin,一般就是指键盘)读取用户输入的数据。
第6行表示输出变量NAME的内容。注意在变量名前边要加上$,否则变量名会作为字符串的一部分处理
执行shell脚本(多种方法)
上面我们编写了一个简单的shell脚本,现在我们让它运行起来。
运行shell脚本有两种方法,一种在新进程中运行,一种是当前shell进程中运行
在新进程中运行shell脚本
在新进程中运行shell脚本有多种方法。
(1)将shell脚本作为程序运行
shell脚本也是一种解释执行的程序,可以在终端直接调用(需要使用 chmod 命令给shell脚本加上执行权限),如下所示:
[root@centos7 ~]#cd /tmp/ #切换到 test.sh 所在的目录
[root@centos7 tmp]#chmod +x test.sh #给脚本文件执行权限
[root@centos7 tmp]#./test.sh #执行脚本文件
Hello world #运行结果
第2行,chmod +x 表示给 test.sh 增加执行权限
第3行中 ./ 表示当前目录,整条命令的意思是执行当前目录下的 test.sh 脚本。如果不写 ./,Linux会到系统路径(由 PATH 环境变量指定)下查找 test.sh ,而系统路径下显然不存在这个脚本,所以会执行失败。
注意:通过这种方式运行脚本,脚本文件第一行的 #!/bin/bash 一定要写对,好让系统查找到正确的解释器
(2)将 shell 脚本作为参数传递给 bash 解释器
你也可以直接运行 bash 解释器,将脚本文件的名字作为参数传递给 bash ,如下所示:
[root@centos7 ~]#cd /tmp/ #切换到 test.sh 所在的目录
[root@centos7 tmp]#/bin/bash test.sh #使用 bash 的绝对路径
Hello World #运行结果
注意:通过这种方式运行脚本,不需要在脚本文件第一行指定解释器信息,指了也没用。
要更加简洁的写法是运行 bash 命令。bash 是一个外部命令,shell 会在 /bin 目录中找到对应的应用程序,也即是 /bin/bash。
[root@centos7 tmp]#bash test.sh
Hello World
这两种写法在本质上是一样的;第一种写法给出了绝对路径,会直接运行 bash 解释器;第二种写法通过 bash 命令找到 bash 解释器所在的目录,然后再运行,只不过多了一个查找的过程而已。
检查是否开启了新进程
可能会有一些疑惑,怎么才能知道开启了新进程呢?既然如此,那就验证一下吧。
Linux 中的每一个进程都有一个唯一的 ID,称为 PID ,使用 $$ 变量就可以获取当前进程的 PID。$$ 是 shell 中的特殊变量。
首先编写如下脚本,并命名为 check.sh
#!/bin/bash
echo $$
然后使用以上两种方式来运行 check.sh
[root@centos7 tmp]#echo $$
1438 #当前进程的PID
[root@centos7 tmp]#chmod +x check.sh
[root@centos7 tmp]#./check.sh
1480 #新进程PID
[root@centos7 tmp]#echo $$
1438 #当前进程PID
[root@centos7 tmp]#/bin/bash check.sh
1481 #新进程PID
进程 PID 都不一样,当然就是两个进程了
在当前进程中运行 shell 脚本
这里需要引入一个新命令----source 命令。source 是 shell
内置命令的一种,它会读取脚本文件中的代码,并依次执行所有语句。你也可以理解为,source
命令会强制执行脚本文件中的全部命令,而忽略脚本文件的权限。
source 命令的用法:
source FILENAME
可简写为 . FILENAME
两种写法效果相同。对于第二种写法,注意点号 . 和文件名中间有一个空格
例如,使用 source 运行上节的 test.sh
[root@centos7 tmp]#source test.sh #使用source
Hello World
[root@centos7 tmp]#. test.sh #使用点号
Hello World
使用 source 命令不用给脚本增加执行权限
检测是否在当前 shell 进程中
我们仍然借助 $$ 变量来输出进程的 PID ,如下所示:
[root@centos7 tmp]#echo $$
1438 #当前进程 PID
[root@centos7 tmp]#source test.sh
1438 #shell脚本所在进程 PID
[root@centos7 tmp]#. test.sh
1438 #shell脚本所在进程 PID
进程 PID 都是一样的,当然是同一个进程了。
总结
注意:脚本中的空白行会被解释器忽略;脚本中,除了shebang,余下所有以 # 开头的行,都会被视作注释行而被忽略,此即为注释行;shell 脚本的运行是通过运行一个子 shell 进程实现的
作为初学者,可能看不懂这些运行方式有什么区别,没关系,暂时留个疑问吧
如果需要在新进