bash:将垂直多行输出分配给变量并获取元素摘要

时间:2018-04-24 20:33:58

标签: bash

我有来自dmidecode命令的输出:

Size: 32 GB Form Factor: DIMM Set: 3 Locator: A1
Size: 16 GB Form Factor: DIMM Set: 3 Locator: A2
Size: 32 GB Form Factor: DIMM Set: 3 Locator: B3
Size: 16 GB Form Factor: DIMM Set: 3 Locator: B4

我需要迭代数组,如果行包含A *,即A1或A2

我需要从该行(32)获取大小并将其添加到包含A的下一行  即32 + 16

我需要为B3 / 4做同样的事情

到目前为止我所得到的是:

IFS='--' read -r -a array <<< $(echo "$DIMM_SIZE_LOCATION")
for element in "${array[@]}";do
        #memory channels belongs cpu socket i.e A1 A2 ..
        SOCKET_CHANNELS=$(echo  "$element"|awk -F":" '{print $5}')
        #size if indevidual dimm
        DIMM_SIZE=$(echo  "$element"|awk -F":" '{print $2}'|grep -v "Error Information Handle"|egrep -o "[0-9]{1,6}")

        if [[ $element = *$SOCKET_CHANNELS* ]];then
                echo $DIMM_SIZE| paste -sd+ | bc
        fi
done

但我没有得到预期的结果

你能建议一个可以完成这项工作的代码吗?

2 个答案:

答案 0 :(得分:2)

另一个awk

$ awk '{a[substr($NF,1,1)]+=$2} 
    END{for(k in a) print k, a[k]}' file

A 48
B 48

答案 1 :(得分:1)

使用sed和awk,假设文本已排序并包含在test.txt文件中

sed -re 's/Size: ([0-9]+).* Locator: ([AB][0-9])/\1 \2/' test.txt \
| gawk '
  {
    if($2 ~ /A[0-9]/) {
      asum+=$1
    } else if($2 ~ /B[0-9]/) {
      bsum+=$1
    }
  }
  END { print "asum=" asum, "bsum=" bsum }
'

正确发出:

asum=48 bsum=48

空白是为了便于阅读;如果紧凑性是一个更重要的目标,它可以改为写在一行,如:

sed -re 's/Size: ([0-9]+).* Locator: ([AB][0-9])/\1 \2/' test.txt  | gawk '{ if($2 ~ /A[0-9]/){ asum+=$1 }else if($2 ~ /B[0-9]/) { bsum+=$1 }} END{ print "asum=" asum, "bsum=" bsum}'