Linux学习——I/O重定向与管道
Linux学习——I/O重定向与管道
6.1 I/O重定向
在/proc虚拟文件系统中,可以查看内核与进程的一些信息
每个进程在运行中都会打开一些文件,每个文件都有一个指定的数字标识
[root@localhost ~]# ps aux | grep passwd
root 43745 0.0 0.1 149400 5280 pts/1 T 13:22 0:00 vim /etc/passwd
[root@localhost ~]# ls /proc/43745/fd
0 1 2 4
[root@localhost ~]# ll /proc/43745/fd
总用量 0
lrwx------. 1 root root 64 11月 25 22:50 0 -> /dev/pts/1
lrwx------. 1 root root 64 11月 25 22:50 1 -> /dev/pts/1
lrwx------. 1 root root 64 11月 25 16:03 2 -> /dev/pts/1
lrwx------. 1 root root 64 11月 25 22:50 4 -> /etc/.passwd.swo
“ 0 ”表示标准输入,“ 1 ”表示标准输出,“ 2 ”表示标准错误,输出到终端,“ 3 ”及以上为常规文件的描述符。
“ date ”——在默认情况下将输出结果显示在终端,此时文件描述符为“1”
[root@localhost ~]# date 1> date.txt
改变描述符为“2”的文件的输出方向
[root@localhost ~]# date 2> date.txt
2023年 11月 25日 星期六 22:58:44 CST
“ cat ”——默认文件描述符为0,输入重定向将键盘输入改为/etc/hosts文件输入
[root@localhost ~]# cat
linux
linux
linux
linux
^Z
[2]+ 已停止 cat
[root@localhost ~]# cat 0< /etc/hosts
127.0.0.1 localhost localhost.localdomain localhost4 localhost4.localdomain4
::1 localhost localhost.localdomain localhost6 localhost6.localdomain6
进程通过文件描述符来管理打开的文件
| 文件描述符 | 通道名 | 说明 | 默认连接 | 用法 |
|---|---|---|---|---|
| 0 | stdin | 标准输入 | 键盘 | 只读 |
| 1 | stdout | 标准输出 | 终端 | 只写 |
| 2 | stderr | 标准错误 | 终端 | 只写 |
| 3+ | filename | 其他文件 | 无 | 可读可写/只读/只写 |
6.1.1 输出重定向
“ > "——覆盖
” >> "——追加
[root@localhost ~]# date >date.txt
[root@localhost ~]# date >date.txt
[root@localhost ~]# date >date.txt
[root@localhost ~]# cat date.txt
2023年 11月 25日 星期六 23:05:50 CST
[root@localhost ~]# date >>date.txt
[root@localhost ~]# date >>date.txt
[root@localhost ~]# date >>date.txt
[root@localhost ~]# cat date.txt
2023年 11月 25日 星期六 23:05:50 CST
2023年 11月 25日 星期六 23:06:10 CST
2023年 11月 25日 星期六 23:06:12 CST
2023年 11月 25日 星期六 23:06:13 CST
-
错误输出重定向
[root@localhost ~]# ls /home/linux [root@localhost ~]# ls /home/linux 2>error.txt -
正确结果与错误结果都输出到相同位置
[root@localhost ~]# ls /home/ /linux &>list.txt -
正确结果与错误结果都输出重定向到相同的位置
[root@localhost ~]# ls /home/ /linux >list.txt 2>&1 -
正确结果保留在文件list.txt,错误结果丢到/dev/null
[root@localhost ~]# ls /home/ /linux >list.txt 2>/dev/null
6.1.2 输入重定向
使用grep过滤root,没有改变输入端,默认为键盘,接着把输入重定向到/etc/passwd(加与不加“ < "结果一样,原理是不一样的)
[root@localhost ~]# grep 'root'
linux
www.baidu.com
^C
[root@localhost ~]# grep 'root' </etc/passwd
root:x:0:0:root:/root:/bin/bash
operator:x:11:0:operator:/root:/sbin/nologin
” dd if=file1 of= file2 “——将文件中读取数据并写入另一个文件中,每次写入1MiB,一共写入两次
[root@localhost ~]# dd if=/dev/zero of=/file01.txt bs=1M count=2
记录了2+0 的读入
记录了2+0 的写出
2097152字节(2.1 MB)已复制,0.0012029 秒,1.7 GB/秒
使用输入重定向与输出重定向的方式也可实现
[root@localhost ~]# dd </dev/zero>file01.txt bs=1M count=2
记录了2+0 的读入
记录了2+0 的写出
2097152字节(2.1 MB)已复制,0.00466903 秒,449 MB/秒
” at “——创建一个计划任务
[root@localhost ~]# at now +5min
at> useradd qf09
at> <EOT>
job 3 at Sat Nov 25 23:25:00 2023
同时创建多个用户
[root@localhost ~]# cat file03.txt
useradd linux01
useradd linux02
useradd linux03
[root@localhost ~]# at now +5min <file03.txt
job 4 at Sat Nov 25 23:27:00 2023
6.1.3 重定向综合案例
- 利用cat命令,在键盘上输入文本按回车键换行,达到输入多行文本的目的
[root@localhost ~]# cat >file03.txt
111
222
333
[root@localhost ~]# cat file03.txt
111
222
333
- 自定义一个结束的符号即EOF
[root@localhost ~]# cat >file03.txt <<EOF
> 111
> 222
> 333
> EOF
[root@localhost ~]#
- 利用重定向建立多行脚本
[root@localhost ~]# cat create_file.sh
cat >file03.txt <<EOF
111
222
aaa
bbb
EOF
[root@localhost ~]# bash create_file.sh
[root@localhost ~]# cat file03.txt
111
222
aaa
bbb
- 在脚本中利用重定向打印消息
[root@localhost ~]# cat create_file.sh
cat <<-EOF
bsdjkcoj
sdjbcoejfpc
ercnfnowpekrf
skjbdjvpewkoor
[root@localhost ~]# bash create_file.sh
create_file.sh:行6: 警告:立即文档在第 1 行被文件结束符分隔 (需要 `EOF')
bsdjkcoj
sdjbcoejfpc
ercnfnowpekrf
skjbdjvpewkoor
多条命令输出重定向
- 如果需要将两条命令都输出都重定向,则需要添加括号
[root@localhost ~]# ls;date &>/dev/null
[root@localhost ~]# ls &>/dev/null;date &>dev/null
bash: dev/null: 没有那个文件或目录
[root@localhost ~]# (ls;date) &>/dev/null
- 让命令在后台运行,并且输出重定向到文件
[root@localhost ~]# (while :; do date ;sleep 2;done) &>date.txt &
[1] 62653
[root@localhost ~]# tailf date.txt
- 终止后台程序
[root@localhost ~]# jobs
[1]- 运行中 ( while :; do
date; sleep 2;
done ) &>date.txt &
[2]+ 已停止 tailf date.txt
[root@localhost ~]# kill %1
[1]- 已终止 ( while :; do
date; sleep 2;
done ) &>date.txt
6.1.4 Subshell
指圆括号里的命令会在另外的进程中执行,当需要让一组命令在不同的目录下执行时,采用这种方法可以不修改主脚本的目录。
对比不加圆括号与加圆括号的区别:
[root@localhost ~]# cd /boot;ls
config-3.10.0-1160.el7.x86_64
efi
grub
grub2
initramfs-0-rescue-dd7b8c7d91a0430db4dac55ab299b957.img
initramfs-3.10.0-1160.el7.x86_64.img
initramfs-3.10.0-1160.el7.x86_64kdump.img
symvers-3.10.0-1160.el7.x86_64.gz
System.map-3.10.0-1160.el7.x86_64
vmlinuz-0-rescue-dd7b8c7d91a0430db4dac55ab299b957
vmlinuz-3.10.0-1160.el7.x86_64
[root@localhost boot]# (cd /boot;ls)
config-3.10.0-1160.el7.x86_64
efi
grub
grub2
initramfs-0-rescue-dd7b8c7d91a0430db4dac55ab299b957.img
initramfs-3.10.0-1160.el7.x86_64.img
initramfs-3.10.0-1160.el7.x86_64kdump.img
symvers-3.10.0-1160.el7.x86_64.gz
System.map-3.10.0-1160.el7.x86_64
vmlinuz-0-rescue-dd7b8c7d91a0430db4dac55ab299b957
vmlinuz-3.10.0-1160.el7.x86_64
如果不希望某些命令的执行对当前shell环境产生影响,请在subshell中执行。
[root@localhost boot]# umask 777;touch file06
[root@localhost boot]# ll file06
----------. 1 root root 0 11月 25 23:47 file06
[root@localhost boot]# umask
0777
[root@localhost boot]# umask 0022
[root@localhost boot]# (umask 777;touch file007)
[root@localhost boot]# ll file007
----------. 1 root root 0 11月 25 23:47 file007
[root@localhost boot]# umask
0022
6.2 进程管道
重定向控制输出到文件,管道控制输出到其他程序
管道的作用是把上一个进程的输出作为下一个进程的输入,利用管道可以把若干个命令连接在一起。
- “ awk ”——快速提取有用的信息,“ -F ”表示指定字段分隔符,默认为空格,“ $7 ”表示第7个字符;
[root@localhost ~]# awk -F: '{print $7}' /etc/passwd
/bin/bash
/sbin/nologin
/sbin/nologin
/sbin/nologin
/sbin/nologin
/bin/sync
/sbin/shutdown
/sbin/halt
/sbin/nologin
/sbin/nologin
/sbin/nologin
/sbin/nologin
- 使用管道符,添加sort命令进行排序(把相同项归类)
[root@localhost ~]# awk -F: '{print $7}' /etc/passwd |sort
/bin/bash
/bin/bash
/bin/bash
/bin/bash
/bin/bash
/bin/bash
/bin/bash
- 添加uniq命令,去掉重复的shell类型
[root@localhost ~]# awk -F: '{print $7}' /etc/passwd |sort |uniq
/bin/bash
/bin/sync
/sbin/halt
/sbin/nologin
/sbin/shutdown
- 添加“ -c ”统计出每种Shell类型的数量
[root@localhost ~]# awk -F: '{print $7}' /etc/passwd |sort |uniq -c
18 /bin/bash
1 /bin/sync
1 /sbin/halt
43 /sbin/nologin
1 /sbin/shutdown
统计网站的访问情况
- 打印所有访问的连接 |过滤访问网站的连接 |打印用户的IP |排序 |去重
[root@localhost ~]# yum -y install httpd
[root@localhost ~]# systemctl start httpd
[root@localhost ~]# systemctl stop firewalld
[root@localhost ~]# ss -an | grep :80 |awk -F ":" '{print $8}' |sort |uniq -c
- 打印当前所有的IP
[root@localhost ~]# ip a | grep 'inet' |awk '{print $2} |awk -F "/" '{print $1}'
- 打印根分区已用空间的百分比
[root@localhost ~]# df -p | grep '/&' |awk '{print $5} |awk -F "%" '{print $1}'
23
tee管道,一条输入满足两个需求
在执行linux命令时,一个进程标准输出通过管道作为下一个进程的标准输入,同时该输出通过tee管道重定向到一个文件或者终端
- 演示管道的作用
[root@localhost ~]# df -p | grep '/&' |awk '{print $5} |awk -F "%" '{print $1}'
23
[root@localhost ~]# df -p | grep '/&' |awk '{print $5} |tee df.txt|awk -F "%" '{print $1}'
23
[root@localhost ~]# cat df.txt
23%

- 若要把输出保存到文件中,又要在终端上看到输出内容,就可以使用tee命令
[root@localhost ~]# date >date.txt
[root@localhost ~]# date | tee date.txt
2023年 11月 26日 星期日 00:08:36 CST
[root@localhost ~]# top -d 1 -b -n 1 >top.txt
[root@localhost ~]# top -d 1 -b -n 1 >tee top.txt
top: unknown option 't'
Usage:
top -hv | -bcHiOSs -d secs -n max -u|U user -p pid(s) -o field -w [cols]
[root@localhost boot]# top -d 1 -b -n 1 |tee top.txt
top - 00:09:46 up 20:48, 10 users, load average: 2.55, 2.48, 2.09
Tasks: 377 total, 2 running, 362 sleeping, 13 stopped, 0 zombie
%Cpu(s): 0.0 us, 21.9 sy, 0.0 ni, 78.1 id, 0.0 wa, 0.0 hi, 0.0 si, 0.0 st
KiB Mem : 3861288 total, 453024 free, 1561836 used, 1846428 buff/cache
KiB Swap: 3145724 total, 3145724 free, 0 used. 1949464 avail Mem
PID USER PR NI VIRT RES SHR S %CPU %MEM TIME+ COMMAND
86597 root 20 0 116968 2088 376 S 23.5 0.1 8:12.66 bash
9 root 20 0 0 0 0 S 5.9 0.0 1:38.69 rcu_sched
23 root rt 0 0 0 0 S 5.9 0.0 0:07.59 migration+
1871 root 20 0 389664 83828 44224 S 5.9 2.2 3:58.11 X
2478 root 20 0 3791480 221044 80344 S 5.9 5.7 8:36.01 gnome-she+
86798 root 20 0 162232 2360 1544 R 5.9 0.1 0:00.02 top
1 root 20 0 194040 7140 4208 S 0.0 0.2 1:02.25 systemd
2 root 20 0 0 0 0 S 0.0 0.0 0:00.26 kthreadd
4 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 kworker/0+
6 root 20 0 0 0 0 R 0.0 0.0 0:18.18 ksoftirqd+
注:在使用管道时,前一个命令的标准错误输出不会被tee读取。
6.3 本章小结

本章主要介绍了输入/输出重定向与进程管道。输入/输出重定向用于规定输入信息的来源或输出信息的保存,管道用于命令之间,从而提高命令输出值的处理效率。
浙公网安备 33010602011771号