1.1 文件相关命令
1.1.1 yum配置阿里镜像源
# 1、备份原来yum源
cd /etc/yum.repos.d/
mv CentOS-Base.repo CentOS-Base.repo_bak
# 2、获取阿里云数据源
curl -o /etc/yum.repos.d/CentOS-Base.repo http://mirrors.aliyun.com/repo/Centos-7.repo
# 3、清除缓存
yum clean all
# 4、生成阿里云镜像源的缓存
yum makecache
1.1.2 vi:文本操作命令
# 创建一个hello的文本
vi hello.txt
# 按 i 进入编辑模式,ESC退出模式
# /+字符=搜索模式,n 跳转下一个相关字符
# 设置临时行号
:set nu
# 跳转到第10行
:10
# yy:复制,pp:粘贴,dd:删除
# 光标下面的内容都删除的话,按三次 9 ,然后按 dd 即可
# gg:跳转第一行,G:跳转最后一行
# 保存退出
:wq
# 查看文本
cat hello.txt
# 覆盖数据
cat a>b
# 追加数据
cat a>>b
1.1.3 文件查找命令
# which 查找
which passwd
# whereis 查找
whereis passwd
# find查找「find 范围 参数 查找对象」
find / -name passwd
# locate 定位
locate passwd
- which(查找可执行文件)
- whereis(查找系统数据库的索引)
- find (实时查找工具,通过遍历指定路径完成文件查找)
- 查找速度略慢
- 精确查找
- 实时查找
- 可能只搜索用户具备读取和执行权限的目录
- locate 非实时查找(数据库查找)
- 查找速度快
- 模糊查找
- 非实时查找
- 搜索的是文件的全路径,不仅仅是文件名
- 可能只搜索用户具备读取和执行权限的目录
1.2 内容相关命令
1.2.1 wc:统计命令
# 查看文本的占用字节,会统计换行符
wc -c hello.txt
# 查看文本的占用字符,会统计换行符
wc -m hello.txt
# 查看文本的总行数
wc -l hello.txt
# 查看文本中最长的一行数据
wc -L hello.txt
# 查看文本中最长的单词总数
wc -W hello.txt
1.2.2 sort:排序命令
# 按照数值正序排
sort -n hello.txt
# 按照数值倒序排
sort -n -r hello.txt
# 按照第几列的数值排序
sort -k 「具体第几列」 -n hello.txt
1.2.3 uniq:去重命令
# 查询重复次数
uniq -c hello.txt
# 返回不重复的行
uniq -u hello.txt
# 去重之前要先排序,先排序,后利用管道去重
sort hello.txt | uniq
1.2.4 head:前n行命令
# 输出前3行
head -3 hello.txt
# 管道组合:查看+翻转排序+去重+前5行
cat hello.txt | sort -nr | uniq | head -5
1.2.5 tail:后n行命令
# 输出后10行的数据
tail -10 hello.txt
1.3 日期相关命令
1.3.1 date:日期操作命令
# 打印日期
date
# 打印格式日期
date +"%Y-%m-%d %H:%M:%S"
2021-08-03 12:25:41
# 当前时间戳
date +%s
# 当前毫秒时间戳
date +%s"000"
# 获取指定时间转化为时间戳
date --date="2048-01-01 00:00:00" +%s
# 获取一天前的时间,并且格式化
date --date="1 days ago" +%Y-%m-%d
# 计算某月多少天
date --date="2021-03-01 1 days ago" +%d
1.4 进程相关命令
1.4.1 ps:显示进程信息
# 查看系统所有进程信息
ps -ef
# 查看过滤后的Java系统进程
ps -ef | grep java
1.4.2 netstat:显示端口信息
# 需要先安装网络工具
yum install -y net-tools
# 查看系统端口占用
netstat -anp
# 查看ssh的22端口是否开启
netstat -anp | grep 22
1.4.3 jps:显示Java进程信息
# jps用于查看Java的进程信息,需要安装jdk
1.4.4 top:动态监控进程信息
# 监控系统的动态进程信息
top
# 退出监控
q
1.4.5 kill:杀掉进程
# 查看系统进程数,得到PID
ps -ef
# 告诉进程,你要自杀了,因为进程在自我结束时会有些收尾工作「推荐」
kill PID
# 强制把进程杀掉,它杀,导致进程没有收尾工作
kill -9 PID
1.5 Linux三剑客
1.5.1 grep:查找
# 查找文本里的内容,二选一即可
grep java hello.txt
cat hello.txt | grep java
# 正则表达式查找
grep ^j hello.txt
# -i:忽略大小写查找java
grep -i java hello.txt
# -n:显示行号
grep -i java -n hello.txt
# 查找Java进程,-v:忽略本身grep进程
ps -ef | grep java | grep -v grep
1.5.2 sed:编辑
# a:在第2行的下面添加数据,结果保存在缓冲区
sed '2a\Big Data' hello.txt
# i:在第5行前面添加数据,
sed '5i\Big Data' hello.txt
# $i:在最后一行的前面添加数据
sed '$i\Big Data' hello.txt
# d:删除第6行的数据
sed '6d' hello.txt
# $d:删除最后一行的数据
sed '$d' hello.txt
# s:替换第2次出现的 j 为 d
sed 's/j/d/2' hello.txt
# g:全文替换,文本中的 j 全部替换为 d
sed 's/j/d/g' hello.txt
# 2s:第二行的 j ,全部替换为 d
sed '2s/j/d/g' hello.txt
# -i:把缓冲区的数据写入文本
sed -i '2a\Big Data' hello.txt
# 实战:修改Redis配置的ip
vi redis.conf
:set nu
==第61行为bind 127.0.0.1==
sed -i 's/127.0.0.1/192.168.110.120/1' redis.conf
1.5.3 awk:分析
# 打印第1列的数据
awk '{print $1}' hello.txt
# 打印所有列的数据
awk '{print $0}' hello.txt
# -F:自定义「:」为分隔符的打印数据
awk -F: '{print $1}' /etc/passwd
# 匹配world字段打印
awk '/world/{print $0}' hello.txt
# 匹配第1列的world字段打印
awk '($1 ~ /world/){print $0}' hello.txt
# 不匹配第2列的world字段打印
awk '($2 !~ /world/){print $0}' hello.txt
1.6 Linux高级配置
1.6.1 静态(ip)配置
# 查看本地ip
ip addr:192.168.53.128
# 查看ip配置文件
cat /etc/sysconfig/network-scripts/ifcfg-ens33
# 修改ip配置文件
vi /etc/sysconfig/network-scripts/ifcfg-ens33
# 修改内容
BOOTPROTO="static"
IPADDR=192.168.53.188
GATEWAY=192.168.53.2
DNS1=192.168.53.2
# 重启网卡
service network restart
# 备注:GATEWAY和DNS1一致
在Win端的VMware可以打开虚拟网络编辑器→VMnet8→NAT设置→查看网关IP
在Mac端的终端
cd /Library/Preferences/VMware\ Fusion/vmnet8
# NAT gateway address
ip = 192.168.53.2
netmask = 255.255.255.0
1.6.2 起名字(hostname)临时设置+永久设置
# 临时设置主机名为bigdata01
hostname bigdata01
# 打印当前主机名
hostname
# 永久设置主机名称
vi /etc/hostname
bigdata01
# 重启机子
reboot -h now
# 打印当前主机名
hostname
1.6.3 防火墙(firewall)临时关闭+永久关闭
# 临时关闭防火墙
systemctl stop firewalld
# 查看防火墙状态
systemctl status firewalld
# 永久关闭防火墙,需要重启
systemctl disable firewalld
# 查看下服务器自启任务中的服务器
systemctl list-unit-files | grep firewalld
1.7 shell编程
1.7.1 Shell脚本
- shell脚本文件名后缀通常是
- .sh
- shell脚本第一行内容是
- #!/bin/bash
- 注意
- **其它行以#开头的表示是注释
1、第一个shell脚本
[root@bigdata01 ~]# mkdir shell
[root@bigdata01 ~]# cd shell/
[root@bigdata01 shell]# vi hello.sh
...
#!/bin/bash
# first command
echo hello world!
2、执行shell脚本
# bash执行
[root@bigdata01 shell]# bash hello.sh
hello world!
# sh执行
[root@bigdata01 shell]# sh hello.sh
hello world!
# bash对应的是/bin目录下面的bash文件
[root@bigdata01 shell]# ll /bin/bash
-rwxr-xr-x. 1 root root 964600 Aug 8 2019 /bin/bash
# sh是一个链接文件,指向的也是/bin目录下面的bash文件,所以这两个命令效果一样
[root@bigdata01 shell]# ll /bin/sh
lrwxrwxrwx. 1 root root 4 Mar 28 20:54 /bin/sh -> bash
# shell脚本不加权限的话是没执行权限的,之所以能运行是因为把hello.sh这个脚本中的内容作为参数直接传给了bash或者sh命令来执行,要自己执行则需要加权限
# 部分权限
[root@bigdata01 shell]# chmod u+x hello.sh
# 完全权限
[root@bigdata01 shell]# chmod 777 hello.sh
# 当前目录执行
[root@bigdata01 shell]# ./hello.sh
hello world!
# 默认会从如下环境目录里找脚本
[root@bigdata01 shell]# echo $PATH
/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/root/bin
# 要在其他目录执行的话,需要修改$PATH
[root@bigdata01 shell]# vi /etc/profile
...
...
...
export PATH=.:$PATH
# 查看修改结果
[root@bigdata01 shell]# echo $PATH
.:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/root/bin
# 随意位置执行脚本
[root@bigdata01 shell]# hello.sh
hello world!
# 查看脚本每段命令的过程
[root@bigdata01 shell]# bash -x hello.sh
+ echo hello 'world!'
hello world!
1.7.2 shell中的变量
- 变量不需要声明
- 初始化也不需要指定类型
- 变量命名
- 只能使用数字、字母和下划线,且不能以数字开头
- 变量赋值是通过”=”进行赋值
[root@bigdata01 shell]# name =zs -bash: name: command not found
[root@bigdata01 shell]# name= zs -bash: zs: command not found
[root@bigdata01 shell]# name2_=zs
[root@bigdata01 shell]# 2name=zs -bash: 2name=zs: command not found
[root@bigdata01 shell]# name2$=zs -bash: name2$=zs: command not found
打印变量,简写形式
[root@bigdata01 shell]# echo $name zs [root@bigdata01 shell]# echo ${name} zs
打印空,因为没有这个变量
[root@bigdata01 shell]# echo $namehehe
变量拼接
[root@bigdata01 shell]# echo ${name}hehe zshehe [root@bigdata01 shell]# echo $name hehe zs hehe
<a name="kVkW1"></a>
### 1.7.3 变量的分类
- 本地变量
- 位置变量
- 环境变量
- 特殊变量
<a name="oV33a"></a>
#### 1、本地变量
- 格式:VAR_NAME=VALUE
- 应用场景
- 在shell脚本中定义一些临时变量时使用
- 对当前shell进程的子shll进程及其它shell进程无效
```basic
# 开启两个ssh,第一台设置的本地变量,第二台访问不到
# 使用pstree查看进程树
[root@bigdata01 shell]# yum install -y psmisc
# 启动进程树
[root@bigdata01 shell]# pstree
├─gssproxy───5*[{gssproxy}]
├─ibus-portal───2*[{ibus-portal}]
├─ibus-x11───2*[{ibus-x11}]
├─irqbalance
├─ksmtuned───sleep
├─libvirtd───16*[{libvirtd}]
├─lsmd
├─lvmetad
├─master─┬─pickup
│ └─qmgr
├─mysqld───26*[{mysqld}]
├─packagekitd───2*[{packagekitd}]
├─polkitd───5*[{polkitd}]
├─pulseaudio───2*[{pulseaudio}]
├─rngd
├─rpcbind
├─rsyslogd───2*[{rsyslogd}]
├─rtkit-daemon───2*[{rtkit-daemon}]
├─smartd
├─sshd───sshd───sshd─┬─bash───pstree
│ └─sftp-server
├─systemd-journal
├─systemd-logind
├─systemd-udevd
├─tuned───4*[{tuned}]
├─udisksd───4*[{udisksd}]
├─upowerd───2*[{upowerd}]
├─wpa_supplicant
└─xdg-permission-───2*[{xdg-permission-}]
# 进入子进程
[root@bigdata01 shell]# bash
[root@bigdata01 shell]# pstree
├─gssproxy───5*[{gssproxy}]
├─ibus-portal───2*[{ibus-portal}]
├─ibus-x11───2*[{ibus-x11}]
├─irqbalance
├─ksmtuned───sleep
├─libvirtd───16*[{libvirtd}]
├─lsmd
├─lvmetad
├─master─┬─pickup
│ └─qmgr
├─mysqld───26*[{mysqld}]
├─packagekitd───2*[{packagekitd}]
├─polkitd───5*[{polkitd}]
├─pulseaudio───2*[{pulseaudio}]
├─rngd
├─rpcbind
├─rsyslogd───2*[{rsyslogd}]
├─rtkit-daemon───2*[{rtkit-daemon}]
├─smartd
├─sshd───sshd───sshd─┬─bash───bash───pstree
│ └─sftp-server
├─systemd-journal
├─systemd-logind
├─systemd-udevd
├─tuned───4*[{tuned}]
├─udisksd───4*[{udisksd}]
├─upowerd───2*[{upowerd}]
├─wpa_supplicant
└─xdg-permission-───2*[{xdg-permission-}]
# 会发现进程树里多了个bash,但是本地变量,子进程依旧无法访问
2、环境变量
- 格式: export VAR_NAME=VALUE
- 应用场景
- 用于设置临时环境变量
- 对子shell进程有效
- 对其它 shell进程无效
- 注意:设置永久环境变量
修改配置,设置永久环境变量
[root@bigdata01 shell]# vi /etc/profile … … … export age=19
生效配置
[root@bigdata01 shell]# source /etc/profile
测试
[root@bigdata01 shell]# echo $age 19
<a name="gI5yv"></a>
#### 3、位置变量
- $0、$1、$2....
- 格式:location.sh abc xyz
- 位置变量
- 相当于java中main函数的args参数
- 可以在shell脚本中动态获取外部参数
```basic
# 编写位置变量
[root@bigdata01 shell]# vi location.sh
#!/bin/bash
echo $0
echo $1
echo $2
echo $3
# 执行脚本
[root@bigdata01 shell]# sh location.sh abc xyz
location.sh
abc
xyz
4、特殊变量
- $?
- 上一条命令的返回状态码,状态码在0~255之间
- $#
$?变量测试
[root@bigdata01 shell]# ll [root@bigdata01 shell]# echo $? 0
[root@bigdata01 shell]# lk -bash: lk: command not found [root@bigdata01 shell]# echo $? 127
$#变量测试
[root@bigdata01 shell]# vi paramnum.sh
!/bin/bash
echo $#
脚本执行
[root@bigdata01 shell]# sh paramnum.sh a b c 3 [root@bigdata01 shell]# sh paramnum.sh a b c d 4
<a name="dNp3P"></a>
#### 5、变量和引号的特殊使用
- '':单引号不解析变量echo'$name
- "":双引号解析变量echo"$name"
- ``:反引号是执行并引用命令的执行结果echo$name
- $(...):是“的另一种写法,效果一样
- 注意:
- echo'"$name"',外单里双,不会解析
- echo"'$name'",外双里单,会解析内容且附上单引号
```basic
# 单引号不解析变量
[root@bigdata01 shell]# name=jack
[root@bigdata01 shell]# echo '$name'
$name
# 双引号解析变量
[root@bigdata01 shell]# name=jack
[root@bigdata01 shell]# echo "$name"
jack
# 反引号
[root@bigdata01 shell]# name=pwd
[root@bigdata01 shell]# echo `$name`
/root/shell
# 外单里双,不会解析
[root@bigdata01 shell]# echo '"$name"'
"$name"
# 外双里单,会解析变量且套上单引号
[root@bigdata01 shell]# echo "'$name'"
'pwd'
1.7.4 shell中的循环判断
- for循环
- while循环
- if判断
1、for循环
# 适合循环步数已定的
[root@bigdata01 shell]# vi for1.sh
#!/bin/bash
for((i=0;i<10;i++))
do
echo $i
done
# 这种格式针对没有规律的列表,或者是有限的几种情况进行迭代是比较方便的
[root@bigdata01 shell]# vi for2.sh
#!/bin/bash
for i in 1 2 3
do
echo $i
done
2、while循环
- 适用于循环次数未知,或不便于使用for直接生成较大列表时
- 测试条件为”真”,则进入循环,测试条件为”假”,则退出循环
- 格式:testEXPR或者[ EXPR ]中括号
- 表达式之间的空格不能少
- 整型测试:
- -gt(大于)
- -lt(小于)
- -ge(大于等于)
- -le(小于。等于)
- -eq(等于)
- -ne(不等于)
- 字符串测试
!/bin/bash
while test 2 -gt 1 do echo yes sleep 1 done
中括号写法
[root@bigdata01 shell]# vi while2.sh
!/bin/bash
while [ 2 -gt 1 ] do echo yes sleep 1 done
字符串测试
[root@bigdata01 shell]# vi while3.sh
!/bin/bash
while [ “abc” = “abc” ] do echo yes sleep 1 done
<a name="Tps2o"></a>
#### 3、if判断
- 单分支
- 双分支
- 多分支
```basic
# 单分支
[root@bigdata01 shell]# vi if1.sh
#!/bin/bash
if [ $# -lt 1 ]
then
echo "not found param"
exit 100
fi
flag=$1
if [ $flag -eq 1 ]
then
echo "one"
fi
# 测试单分支
[root@bigdata01 shell]# sh if1.sh
not found param
[root@bigdata01 shell]# echo $?
100
# 双分支
[root@bigdata01 shell]# vi if2.sh
#!/bin/bash
if [ $# -lt 1 ]
then
echo "not found param"
exit 100
fi
flag=$1
if [ $flag -eq 1 ]
then
echo "one"
else
echo "not support"
fi
# 测试双分支
[root@bigdata01 shell]# sh if2.sh 1
one
[root@bigdata01 shell]# sh if2.sh 2
not support
# 多分支
[root@bigdata01 shell]# vi if3.sh
#!/bin/bash
if [ $# -lt 1 ]
then
echo "not found param"
exit 100
fi
flag=$1
if [ $flag -eq 1 ]
then
echo "one"
elif [ $flag -eq 2 ]
then
echo "two"
elif [ $flag -eq 3 ]
then
echo "three"
else
echo "not support"
fi
# 测试多分支
[root@bigdata01 shell]# sh if3.sh 1
one
[root@bigdata01 shell]# sh if3.sh 2
two
[root@bigdata01 shell]# sh if3.sh 3
three
[root@bigdata01 shell]# sh if3.sh 4
not support
1.7.5 shell扩展
- 后台模式运行脚本:nohup xxx.sh &
- 标准输出(1)、标准错误输出(2)、重定向( >或者 >>)
- 黑洞:nohup hello.sh >/dev/null 2>&1 &
# 有什么脚本,程序想放后台执行的,则使用
nohup xxx.sh &
# 标准输出:正确输出(1)
[root@bigdata01 shell]# ll
total 2
-rw-r--r--. 1 root root 48 Apr 3 17:32 for1.sh
-rw-r--r--. 1 root root 43 Apr 3 17:40 for2.sh
# 标准错误输出:错误输出(2)
[root@bigdata01 shell]# lk
-bash: lk: command not found
# 正确数据输出重定向到文本里
[root@bigdata01 shell]# ll 1> a.txt
[root@bigdata01 shell]# more a.txt
...
# 错误数据输出重定向到文本里
[root@bigdata01 shell]# lk 2> a.txt
[root@bigdata01 shell]# more a.txt
...
# 把脚本放到后台执行,并且控制台的命令数据都不保存
nohup hello.sh >/dev/null 2>&1 &