我如何根据 ip 地址对多行进行排序?

2017-04-14 15:48:33 +08:00
 ioiioi

譬如说我有以下的多行:

user-bind static ip-address 10.199.27.246 mac-address 00d0-d0b6-c09a vlan 7
user-bind static ip-address 10.199.27.223 mac-address f0de-f127-e980 vlan 7
user-bind static ip-address 10.199.28.26 mac-address 3c97-0ecd-7797 vlan 7
user-bind static ip-address 10.199.27.192 mac-address 0027-19a3-516d vlan 7
user-bind static ip-address 10.199.29.199 mac-address 000f-e2d2-5a38 vlan 7
user-bind static ip-address 10.199.27.98 mac-address 0090-27b6-cd8c vlan 7
user-bind static ip-address 10.199.27.124 mac-address 047d-7bd4-1eaf vlan 7

ip 地址有 3 个网段: 10.199.27.0/24, 10.199.28.0/24, 10.199.29.0/24 我想排列成:

user-bind static ip-address 10.199.27.98 mac-address 0090-27b6-cd8c vlan 7
user-bind static ip-address 10.199.27.124 mac-address 047d-7bd4-1eaf vlan 7
user-bind static ip-address 10.199.27.192 mac-address 0027-19a3-516d vlan 7
user-bind static ip-address 10.199.27.223 mac-address f0de-f127-e980 vlan 7
user-bind static ip-address 10.199.27.246 mac-address 00d0-d0b6-c09a vlan 7
user-bind static ip-address 10.199.28.26 mac-address 3c97-0ecd-7797 vlan 7
user-bind static ip-address 10.199.29.199 mac-address 000f-e2d2-5a38 vlan 7

使用 cut 、 sort 、 awk 、 sed 能实现吗?

4514 次点击
所在节点    Linux
34 条回复
jigloo
2017-04-14 15:52:04 +08:00
cat 1.txt | sort -h
msg7086
2017-04-14 16:01:37 +08:00
@jigloo sort 不能直接读文件么
ioiioi
2017-04-14 16:02:31 +08:00
抱歉,我用的是 babun on windows , sort -h 是起什么作用?
jigloo
2017-04-14 16:06:56 +08:00
@msg7086
习惯了

@ioiioi
cat 1.txt | sort -t. -k1 -k2 -k3 -k4
ioiioi
2017-04-14 16:08:55 +08:00
我现在的方法比较蠢:

```
cat raw.txt | cut -d " " -f 4 > ip.list.txt
cat ip.list.txt | sort -t . -k 3,3n -k 4,4n > ip.list.sorted.txt # <1>
```
<1> https://www.cyberciti.biz/faq/unix-linux-shell-script-sorting-ip-addresses/

得到的结果只是一串排序后的 ip ,剩余字符串就全部丢失了。
Glink
2017-04-14 16:47:38 +08:00
cat test.txt |sort -t. -k 3,3n -k4,4n
直接这么写就可以了
gouchaoer
2017-04-14 16:50:08 +08:00
把 ip 转化成 unsigned int ,然后快拍。。。。为啥一定要用难用的 sort cut 之类的,用熟悉的语言就 ok 了
ioiioi
2017-04-14 16:57:19 +08:00
@Glink wow !我直接用了 sort -t . -k 3,3n -k 4,4n source.txt > output.txt
不过,假如有一些行的 ip 地址之前包含了“.”,而有一些行又没有的话,又该怎么处理?因为无法用-k 3 来限定排序的字段了。
我想找一个比较通用的处理办法。
ioiioi
2017-04-14 16:57:57 +08:00
@gouchaoer
:-<
我不是程序员,只是一个普通的 linux 用户,会一点 shell 。
jigloo
2017-04-14 17:06:31 +08:00
哦,那可以试下这个

cat 1.txt | awk '{print $4" "$0}' | sort -t. -k3,3n -k4,4n | awk '{for (i=2; i<NF; i++) printf $i " "; print $NF}'
realpg
2017-04-14 17:07:08 +08:00
EXCEL 大法好……
gouchaoer
2017-04-14 17:07:49 +08:00
@ioiioi 不是码农用 linux 干嘛,那么难用
ioiioi
2017-04-14 17:22:17 +08:00
@realpg
excel 比较繁琐,主要是没法在妹子面前装 13 ,:-)
ioiioi
2017-04-14 17:22:50 +08:00
@gouchaoer 嗯,这的确是一个问题,令我陷入了深深地思考....
ioiioi
2017-04-14 17:28:42 +08:00
@jigloo 我得好好消化一下,如果你能简答说明下思路更好,我大概知道 awk '{print $4" "$0}'是为了截取 ip 地址, sort 是为了排序,但是后面那个 awk 就完全不知道是干嘛了。
jigloo
2017-04-14 17:46:50 +08:00
@ioiioi

后面做繁琐了,这个更清楚点。

cat 1.txt | awk '{print $4 $0}' | sort -t. -k3,3n -k4,4n | awk '{sub($1 FS,""); print}'

你先不要执行整个,把这几个管道一个个加上,然后在执行,就能清楚这个过程了。
realpg
2017-04-14 18:02:28 +08:00
@ioiioi #13
一点也不繁琐
这种问题从来都是 excel 解决 excel 处理各种增减,排序,简单算法比变成省事儿多了……
ioiioi
2017-04-14 18:18:33 +08:00
@jigloo got it , thanks !
lilydjwg
2017-04-14 18:23:04 +08:00
@gouchaoer #7 因为只有 shell 能在一两行之内搞定这种事啊。
lilydjwg
2017-04-14 18:31:27 +08:00
其实你可以用 piep ,方便好用又容易理解:

piep -e 'from socket import inet_aton' 'pp.sortby(fn=lambda x: inet_aton(x.split()[3]))' < input

piep 的文档: http://gfxmonk.net/dist/doc/piep/

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/354878

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX