八、Linux 常用 Shell 命令,控制台的快捷键以及 Shell 编程(中)
发布日期:2021-07-01 02:08:29 浏览次数:2 分类:技术文章

本文共 4849 字,大约阅读时间需要 16 分钟。

@Author : Runsen

@Date:2020/9/11

文章是Runsen在Gitchat付费文章分享:

顺便同步到CSDN中,这里设置了VIP,不好意思!!八月份写的,有些时间了。

文章目录

Shell脚本编程

所谓脚本,就是把众多命令写入一个文件中,让其按照一定的逻辑顺序执行,以完成一个具体的功能。而在Linux的shell编译环境下,shell编程与众多编程语言一样,也有其独立的语法。

打开文本编辑器(可以使用 vi/vim 命令来创建文件),新建一个文件 test.sh,扩展名为 sh(sh代表shell)。

maoli@ubuntu:~$ vim test.sh#!/bin/bashecho "Hello World !"

变量

变量名不加美元符号($,PHP语言中变量需要)。比如在shell中 定义变量name = Runsen,而在php就是$name = Runsen

使用一个定义过的变量,只要在变量名前面加美元符号即可,如:$name或者${name}。变量名外面的花括号是可选的,加不加都行。

变量支持字符串类型,浮点等类型,常见有这 3 个前缀:

  • unset:删除变量
  • readonly:标记只读变量
  • export:指定全局变量
#!/bin/bash # 定义普通变量,没有特殊字符或者空格,可以不用引号CITY=Dongguan# 定义全局变量export NAME=Runsen# 定义只读变量readonly AGE=20# 打印变量的值echo $CITYecho $NAMEecho $AGE# 删除 CITY 变量unset CITY# 不会输出 Dongguanecho $CITY

预定义变量

预定义变量常用来获取命令行的输入,有下面这些:

$0 :脚本文件名$1-9 :第 1-9 个命令行参数名$# :命令行参数个数$@ :所有命令行参数$* :所有命令行参数$? :前一个命令的退出状态,可用于获取函数返回值$$ :执行的进程 ID

下面我们看一个预定义变量例子:

maoli@ubuntu:~$ vim hello.sh#!/bin/bash echo "\$0 = $0"echo "\$1 = $1"echo "\$2 = $2"echo "\$# = $#"echo "\$@ = $@"echo "\$* = $*"echo "\$$ = $$"echo "\$? = $?"maoli@ubuntu:~$ ./hello.sh 1 2 3 4 5 # 程序名$0 = ./hello.sh# 第一个参数$1 = 1# 第二个参数$2 = 2# 一共有 5 个参数$# = 5# 打印出所有参数$@ = 1 2 3 4 5# 打印出所有参数$* = 1 2 3 4 5# 进程 ID$$ = 9450# 之前没有执行其他命令或者函数$? = 0

数组和运算符

数组

数组中可以存放多个值。Bash Shell 只支持一维数组(不支持多维数组),初始化时不需要定义数组大小。Shell 数组用括号来表示,元素用"空格"符号分割开,举例如下:

my_array=(A B "C" D)

我们也可以使用下标来定义数组:

array_name[0]=value0array_name[1]=value1array_name[2]=value2

读取数组

my_array=(A B "C" D)echo "第一个元素为: ${my_array[0]}"echo "第二个元素为: ${my_array[1]}"echo "第三个元素为: ${my_array[2]}"echo "第四个元素为: ${my_array[3]}"

获取数组中的所有元素

使用@ 或 * 可以获取数组中的所有元素,例如:

my_array[0]=Amy_array[1]=Bmy_array[2]=Cmy_array[3]=Decho "数组的元素为: ${my_array[*]}"echo "数组的元素为: ${my_array[@]}"

获取数组的长度

获取数组长度的方法与获取字符串长度的方法相同,例如:

my_array[0]=Amy_array[1]=Bmy_array[2]=Cmy_array[3]=Decho "数组元素个数为: ${#my_array[*]}"echo "数组元素个数为: ${#my_array[@]}"

运算符

val=`expr 2 + 2`echo "两数之和为 : $val"

两点注意:

  • 表达式和运算符之间要有空格,例如 2+2 是不对的,必须写成 2 + 2,这与我们熟悉的大多数编程语言不一样。
  • 完整的表达式要被 包含,注意这个字符不是常用的单引号,在 Esc 键下边。
运算符 说明 举例
+ 加法 expr $a + $b 结果为 30。
- 减法 expr $a - $b 结果为 -10。
* 乘法 expr $a \* $b 结果为 200。
/ 除法 expr $b / $a 结果为 2。
% 取余 expr $b % $a 结果为 0。
= 赋值 a=$b 将把变量 b 的值赋给 a。
== 相等。用于比较两个数字,相同则返回 true。 [ $a == $b ] 返回 false。
!= 不相等。用于比较两个数字,不相同则返回 true。 [ $a != $b ] 返回 true。

关系运算符

关系运算符只支持数字,不支持字符串,除非字符串的值是数字。

下表列出了常用的关系运算符,假定变量 a 为 10,变量 b 为 20:

运算符 说明 举例
-eq 检测两个数是否相等,相等返回 true。 [ $a -eq $b ] 返回 false。
-ne 检测两个数是否相等,不相等返回 true。 [ $a -ne $b ] 返回 true。
-gt 检测左边的数是否大于右边的,如果是,则返回 true。 [ $a -gt $b ] 返回 false。
-lt 检测左边的数是否小于右边的,如果是,则返回 true。 [ $a -lt $b ] 返回 true。
-ge 检测左边的数是否大于等于右边的,如果是,则返回 true。 [ $a -ge $b ] 返回 false。
-le 检测左边的数是否小于等于右边的,如果是,则返回 true。 [ $a -le $b ] 返回 true。

流程控制

if判断语句,下面我们写一个简单判断语句。

maoli@ubuntu:~$ vim hello.sh#!/bin/bash # read 的方法就python中的input,适用于终端命令提示符read VAR# 下面这两种判断方法都可以,使用 [] 注意左右加空格#if test $VAR -eq 10if [ $VAR -eq 10 ]then    echo "true"else    echo "false"fimaoli@ubuntu:~$ sh hello.sh 10true

for 循环和Python没有什么区别,挺简单的。如果运行for循环报错Syntax error: Bad for loop variable,需要使用命令sudo dpkg-reconfigure dash,然后在在选择项中选No

原因:代码对于标准bash而言没有错,因为Ubuntu为了加快开机速度,用dash代替了传统的bash,是dash在捣鬼。

下面是for循环的shell代码

maoli@ubuntu:~$ vim hello.sh#!/bin/bash # 普通 for 循环 declare声明变量-ideclare -i SUM=0for ((i=1;i<=100;i+=1))do        let SUM+=$idoneecho $SUM# loop 依次代表每个元素 for loop in 1 2 3 4 5do    echo "The value is: $loop"done# VAR 依次代表每个元素 ,{}产生连续数字for VAR in {
1..3}do echo $VARdonemaoli@ubuntu:~$ sh hello.sh 5050The value is: 1The value is: 2The value is: 3The value is: 4The value is: 5123#也可以写成一行,方便在命令行直接运行,注意空格和;号:maoli@ubuntu:~$ for VAR in {
1..3}; do echo $VAR; done123

Linux 问题处理

下面问题是我在用 Linux 时,经常出来,对此,个人做一个简单的记录。

不知道文件放在哪里,如何查找文件

很多的时候,我搭建 Hadoop 等环境的时候,不知道下载的安装包放在哪里,其实使用 locate 命令就可以了。

下面是我的具体演示。

locate:通过文件名查找文件。

语法:

locate [-d ][--help][--version][范本样式...]

举例:查找 passwd 文件。

locate passwd

搜索 etc 目录下所有以 my 开头的文件:

locate /etc/my

这里说下:在用 whereis 和 locate 查找文件时,有时会找到已经被删除的数据,或者刚刚建立文件,却无法查找到,原因就是因为数据库文件没有被更新。为了避免这种情况,可以在使用 locate 之前,先使用 updatedb 命令,手动更新数据库。整个 locate 工作其实是由四部分组成的。

新增的文件无法 locate,使用 updatedb:

[root@cent7 ~]# touch new.txt[root@cent7 ~]# locate new.txt[root@cent7 ~]# updatedb[root@cent7 ~]# locate new.txt/root/new.txt

还有 find:在目录层次结构中查找文件。

忘记密码解决,怎么登录

有几次,我忘了 CentOS 7 的用户密码,对此也百度折腾了下。下面介绍解决方法,我以 CentOS 7 为例。

在启动选择内核版本的时候按上下键,令画面停住。

CentOS 7 每次会有两个版本的内核供选择,简单的来说就是一个主内核版本,一个副内核版本,如果以后内核升级失败无法使用新内核重启时,可以通过这个界面选择旧内核重启进行修复。

选择好了内核之后,按下 e 键,进入编辑界面。

找到以 linux16 开头的那一行,在行尾加上如下几句话:

  • 如果是物理机,添加:rd.break
  • 如果是虚拟机,添加:rd.break console=tty0

这里我用的是虚拟机,所以添加 rd.break console=tty0,如下图所示:

然后按 Ctrl+x 进行启动。

进入 shell 环境之后,进行如下操作。

  1. 将根目录重新挂载,模式可写:
switch_root:/# mount -o rw,remount /sysroot
  1. 变更目录至根目录下:
switch_root:/# chroot /sysroot
  1. 更改密码:
sh-4.2# passwd
  1. 如果安装的是中文系统,此时会出现乱码,可以根据经验直接输入,也可输入以下命令,当次变更语言为英语。
sh-4.2# LANG=en_US
  1. 如果 SELinux 开启需要更新 SELinux 上下文,只要创建下面的文件即可。
sh-4.2# touch /.autorelabel
  1. 退出重启。
sh-4.2# exitswitch_root:/# exit

转载地址:https://maoli.blog.csdn.net/article/details/108543207 如侵犯您的版权,请留言回复原文章的地址,我们会给您删除此文章,给您带来不便请您谅解!

上一篇:为了OFFER,花了几个小时,刷下Leetcode链表算法题
下一篇:六十一、深入学习位运算

发表评论

最新留言

表示我来过!
[***.240.166.169]2024年04月09日 18时42分25秒