基于Born字段对多行信息块按出生日期从旧到新排序的Shell脚本需求
基于出生日期排序空行分隔的信息块(Bash实现)
需求说明
我有一个包含如下内容的文件:
Name: Karl Born: 2003-07-06 17:21:36.964 State: Germany Hobby: Videogames Name: Albert Born: 2003-07-05 18:16:19.369 State: UK Hobby: Soccer Name: Mark Born: 2003-06-15 16:58:21.201 State: Italy Hobby: Jogging
需要编写Shell脚本,基于Born字段将空行分隔的信息块按出生日期从旧到新排序,正确输出如下:
Name: Mark Born: 2003-06-15 16:58:21.201 State: Italy Hobby: Jogging Name: Albert Born: 2003-07-05 18:16:19.369 State: UK Hobby: Soccer Name: Karl Born: 2003-07-06 17:21:36.964 State: Germany Hobby: Videogames
要求仅用Bash环境实现,不能使用Perl或Python。
实现脚本
以下是可直接运行的Bash脚本,假设目标文件名为data.txt,可自行替换为你的文件名:
#!/bin/bash input_file="data.txt" # 提取每个块的Born字段作为排序键,拼接后排序,再恢复格式 awk ' BEGIN { RS = ""; FS = "\n" } { for (i=1; i<=NF; i++) { if ($i ~ /^Born: /) { sort_key = substr($i, 7) break } } print sort_key "|||" $0 } ' "$input_file" | sort | awk ' BEGIN { first_block = 1 } { if (!first_block) print "" print substr($0, index($0, "|||") + 4) first_block = 0 } '
脚本工作原理
- 第一个awk处理:
- 将空行设为记录分隔符(
RS = ""),把每个用户的4行信息作为单个记录处理。 - 遍历记录内的每一行,找到以
Born:开头的行,提取冒号后的日期时间作为排序键。 - 用
|||作为分隔符,将排序键和整个信息块拼接后输出,为后续排序做准备。
- 将空行设为记录分隔符(
- sort排序:
- ISO格式的日期时间字符串可以直接按字典序排序,从小到大排序就对应出生日期从旧到新。
- 第二个awk处理:
- 去掉排序键和分隔符,还原原始信息块。
- 控制信息块之间的空行输出,避免第一个块前出现空行。
内容的提问来源于stack exchange,提问作者Dave Dolone
相关产品推荐
相关产品推荐

