shell技巧-Parallel命令行并行工具(xargs增强版)
之前写过xargs的高级用法,但是在工作中发现xargs并不能实现所有的需求。我发现xargs存在下面两个痛点。
- 本身无法调整格式化参数的位置
- 控制命令行并行的数量支持不友好
为什么要用parallel代替xargs?
xargs能实现的功能parallel都能做。
交换参数的位置
第一个可以通过sh命令来解决,但是本身不优雅。比如
root@VM-32-8-ubuntu:~# seq 1 6 | xargs -n2 echo 1 2 3 4 5 6 root@VM-32-8-ubuntu:~# seq 1 6 | xargs -n2 sh -c 'echo $2 $1' _ 2 1 4 3 6 5 root@VM-32-8-ubuntu:~# seq 1 6 | parallel -n2 echo {2} {1} 2 1 4 3 6 5
虽然可以通过sh -c 这种曲线救国的方式来交换参数位置,但是每条命令都得新启动一个shell来执行。
经测试在数据量大的情况下,xargs sh -c
效率非常低下。极为不推荐!
root@VM-32-8-ubuntu:~# seq 1 6 | xargs -n2 | awk '{print $2,$1}' 2 1 4 3 6 5
写这篇文章的时候突然想到还能用xargs配合awk来交换列。
root@VM-32-8-ubuntu:~# seq 1 6 | xargs -n2 | awk '{print $2,$1}' 2 1 4 3 6 5
命令并行数量
可以使用 & 的方式让命令全部在后台执行,但是会一次性全部执行,占满CPU甚至出现卡顿的情况。
虽然 xargs 也支持 -P 多个CPU同时运行。
-P, --max-procs=MAX-PROCS run at most MAX-PROCS processes at a time
比如我们写一个ping探测内网存活的shell命令。
root@VM-32-8-ubuntu:~# ifconfig eth0 | grep inet inet 172.19.32.8 netmask 255.255.240.0 broadcast 172.19.47.255 root@VM-32-8-ubuntu:~# root@VM-32-8-ubuntu:~# seq 0 255 | sed 's/^/172.19.32./g' | xargs -n1 sh -c 'ping -c1 $1 &' _ PING 172.19.32.1 (172.19.32.1) 56(84) bytes of data. ..... PING 172.19.32.8 (172.19.32.8) 56(84) bytes of data. 64 bytes from 172.19.32.8: icmp_seq=1 ttl=64 time=0.044 ms --- 172.19.32.8 ping statistics --- 1 packets transmitted, 1 received, 0% packet loss, time 0ms rtt min/avg/max/mdev = 0.044/0.044/0.044/0.000 ms PING 172.19.32.9 (172.19.32.9) 56(84) bytes of data. ......
通过 & 方式,相当于一瞬间起了256个shell来执行ping命令。这种方式并不优雅,如果用这种方式扫b段,那就要同时起65536个子进程,CPU???
使用sh -c 每次还需要多起一个shell,不使用sh -c 则又不支持调整参数位置。
用parallel的写法如下
seq 1 255 | sed 's/^/172.19.32./g' | parallel -j5 ping {1} -c1赞赏
微信赞赏支付宝赞赏
发表评论