bash - 如何将一个输出中的特定行添加到另一个输出中的特定行?

标签 bash shell awk

我的输出有问题。

所以我从一个命令得到了这个输出。

$ sudo /opt/MegaRAID/MegaCli/MegaCli64 -LdPdInfo -a0

Name               : Virtual_Disk0  
RAID Level         : 1 
State              : Optimal  
Number Of Drives   : 2  

Name               : Virtual_Disk1  
RAID Level         : 5 
State              : Optimal  
Number Of Drives   : 6  

Name               : Virtual_Disk2  
RAID Level         : 0 
State              : Optimal  
Number Of Drives   : 2 

我有另一个命令的第二个输出。

$ sudo /opt/MegaRAID/MegaCli/MegaCli64 -LdPdInfo -a0 \
> | xargs \
> | sed -r 's/(Slot Number:)(\s[0-9]+)/\2,/g' \
> | sed 's/(Target Id: .)/Physical Drives ids:/g'

Virtual Drive: 0 Physical Drives ids:  0,  1,
Virtual Drive: 1 Physical Drives ids:  2,  3,  4,  5,  6,  7,
Virtual Drive: 2 Physical Drives ids:  8,  9,

所以,我想合并两个输出。虚拟磁盘# 末尾的数字必须与虚拟驱动器后的第一个数字匹配:#

所以,我希望它看起来像这样:

Name               : Virtual_Disk0  
RAID Level         : 1 
State              : Optimal  
Number Of Drives   : 2  
Virtual Drive: 0 Physical Drives ids:  0,  1,

Name               : Virtual_Disk1  
RAID Level         : 5 
State              : Optimal  
Number Of Drives   : 6  
Virtual Drive: 1 Physical Drives ids:  2,  3,  4,  5,  6,  7,

Name               : Virtual_Disk2  
RAID Level         : 0 
State              : Optimal  
Number Of Drives   : 2 
Virtual Drive: 2 Physical Drives ids:  8,  9,

条目始终匹配,并且顺序相同。

我已经尝试过这个:

$ sudo /opt/MegaRAID/MegaCli/MegaCli64 -LdPdInfo -a0 ; \
> sudo /opt/MegaRAID/MegaCli/MegaCli64 -LdPdInfo -a0 | \
> xargs \
> | sed -r 's/(Slot Number:)(\s[0-9]+)/\2,/g' \
> | sed 's/(Target Id: .)/Physical Drives ids:/g'

Name               : Virtual_Disk0  
RAID Level         : 1 
State              : Optimal  
Number Of Drives   : 2  

Name               : Virtual_Disk1  
RAID Level         : 5 
State              : Optimal  
Number Of Drives   : 6  

Name               : Virtual_Disk2  
RAID Level         : 0 
State              : Optimal  
Number Of Drives   : 2 
Virtual Drive: 0 Physical Drives ids:  0,  1,
Virtual Drive: 1 Physical Drives ids:  2,  3,  4,  5,  6,  7,
Virtual Drive: 2 Physical Drives ids:  8,  9,

最佳答案

在我的环境中模拟 MegaCli64 输出:

$ cat mega1.out
Name               : Virtual_Disk0
RAID Level         : 1
State              : Optimal
Number Of Drives   : 2

Name               : Virtual_Disk1
RAID Level         : 5
State              : Optimal
Number Of Drives   : 6

Name               : Virtual_Disk2
RAID Level         : 0
State              : Optimal
Number Of Drives   : 2

$ cat mega2.out
Virtual Drive: 0 Physical Drives ids:  0,  1,
Virtual Drive: 1 Physical Drives ids:  2,  3,  4,  5,  6,  7,
Virtual Drive: 2 Physical Drives ids:  8,  9,

一个awk想法:

awk '
FNR==NR             { drives[$3] = $0; next }                  # 1st file: use 3rd field as index for storing entire line
$NF~/^Virtual_Disk/ { if (match($NF,/[0-9]+$/))                # 2nd file: last field starts with "Virtual_Disk"; look for number on end of last field and if found ...
                         driveno = substr($NF,RSTART,RLENGTH)  # extract said number
                    }
1                                                              # 2nd file: print current line
/^Number Of Drives/ { if (driveno in drives)                   # 2nd file: line starts with "^Number Of Drives"; if we have a matching record in the drives[] array then ...
                         print drives[driveno]                 # print said line to stdout and ...
                      driveno=""                               # clear our variable
                    }
' <(cat mega2.out) <(cat mega1.out)                            # NOTE: process 2nd set of MegaCli64 output *first*

这会生成:

Name               : Virtual_Disk0
RAID Level         : 1
State              : Optimal
Number Of Drives   : 2
Virtual Drive: 0 Physical Drives ids:  0,  1,

Name               : Virtual_Disk1
RAID Level         : 5
State              : Optimal
Number Of Drives   : 6
Virtual Drive: 1 Physical Drives ids:  2,  3,  4,  5,  6,  7,

Name               : Virtual_Disk2
RAID Level         : 0
State              : Optimal
Number Of Drives   : 2
Virtual Drive: 2 Physical Drives ids:  8,  9,

在 OP 的实际环境中,他们需要进行以下更改:

# replace this:

' <(cat mega2.out) <(cat mega1.out)

# with this:

' <(sudo /opt/MegaRAID/MegaCli/MegaCli64 -LdPdInfo -a0 | xargs | sed ... | sed ... ) <(sudo /opt/MegaRAID/MegaCli/MegaCli64 -LdPdInfo -a0)

注意:我只是复制 OP 提供的 MegaCli64 命令和输出; OP 将需要验证这些命令和/或根据需要进行编辑

关于bash - 如何将一个输出中的特定行添加到另一个输出中的特定行?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/75869656/

相关文章:

bash - 为什么 'ls *[[:digit:]*]' 有效但 'ls *[[:digit:]*]_[[:digit:]*]' 无效?

linux - 输出重定向到文件

linux - 如何在 BASH 中打印整行

linux - 如何压缩目录中大于一定大小的文件?

node.js - 如何将元数据添加到 mac/linux 上的文件夹

linux - Bash IFS,在函数调用中被打断

linux - 如何使用 shell 脚本从 dhcp.lease 文件中提取 IP 地址、MAC 地址和名称?

linux - bash 如何用于将标准输出通过管道传输到脚本并写入终端?

bash - gnu并行中的两对双引号冲突

linux - 使用 Grep、Awk 等解析大量文件