阅读在shell脚本文件,并选择线路的部分(Reading a file in a shell sc

2019-09-29 15:32发布

这可能是非常基本的,我想在发生读取文件。

然后程序应该找到的所有出现"CallTilEdb"在文件Hendelse.logg

CallTilEdb         8
CallCustomer       9
CallTilEdb         4
CustomerChk        10
CustomerChk        15
CallTilEdb         16

和总结,然后右列。 对于这种情况下,将8 + 4 + 16,所以输出我希望将是28

我不知道如何做到这一点,这是据我已经与得到vistid.sh

#!/bin/bash
declare -t filename=hendelse.logg
declare -t occurance="$1"
declare -i sumTime=0

while read -r line
do
    if [ "$occurance" = $(cut -f1 line) ]       #line 10
    then
        sumTime+=$(cut -f2 line)
    fi
done < "$filename"

所以在终端的执行将

vistid.sh CallTilEdb

但现在我得到的错误是:

/home/user/bin/vistid.sh: line 10: [: unary operator expected

Answer 1:

你有一个很好的方法,但也许你可以使用awk做同样的事情相当...快!

$ awk -v par="CallTilEdb" '$1==par {sum+=$2} END {print sum+0}' hendelse.logg
28

它可能看起来有点怪,如果你还没有使用的awk,到目前为止,但在这里是做什么的:

  • -v par="CallTilEdb"提供一个参数awk ,使我们可以使用par作为脚本的变量。 你也可以做-v par="$1" ,如果你想使用提供给脚本参数变量。
  • $1==par {sum+=$2}这意味着:如果第一字段是相同的变量的内容par ,然后添加第二列的值到计数器sum
  • END {print sum+0}这意味着:一旦你从处理文件完成后,打印的内容sum 。 该+0使得awk打印0的情况下, sum没有设置...也就是说,如果没有被发现。

如果你真的想使用bash,你可以使用,使其read有两个参数,使您不必利用cut处理的值,以及一些算术运算总结的值:

#!/bin/bash
declare -t filename=hendelse.logg
declare -t occurance="$1"
declare -i sumTime=0

while read -r name value                  # read both values with -r for safety
do
    if [ "$occurance" == "$name" ]; then  # string comparison
       ((sumTime+=$value))                # sum
    fi
done < "$filename"

echo "sum: $sumTime"

因此,它的工作原理是这样的:

$ ./vistid.sh CallTilEdb
sum: 28
$ ./vistid.sh CustomerChk
sum: 25


Answer 2:

首先你需要改变你叫切方式:

$( echo $line | cut -f1 )

在第10行,你错过了评价:

if [ "$occurance" = $( echo $line | cut -f1 ) ]

那么你可以通过做总结:

sumTime=$[ $sumTime + $( echo $line | cut -f2 ) ]

但你也可以使用不同的方法和放线值的数组,最终脚本将是这样的:

#!/bin/bash
declare -t filename=prova
declare -t occurance="$1"
declare -i sumTime=0

while read -a line
do
    if [ "$occurance" = ${line[0]} ]
    then
        sumTime=$[ $sumtime + ${line[1]} ]
    fi
done < "$filename"

echo $sumTime


Answer 3:

对于参考,

id="CallTilEdb"
file="Hendelse.logg"

sum=$(echo "0 $(sed -n "s/^$id[^0-9]*\([0-9]*\)/\1 +/p" < "$file") p" | dc)
echo SUM: $sum

版画

SUM: 28
  • 所述sed从含有给定id的线,例如提取号码CallTilEdb
  • 并将它们打印格式number +
  • echo准备一个字符串, 0 8 + 16 + 4 + p什么是计算在RPN格式
  • 直流做计算

另一种变体:

sum=$(sed -n "s/^$id[^0-9]*\([0-9]*\)/\1/p" < "$file" | paste -sd+ - | bc)
#or
sum=$(grep -oP "^$id\D*\K\d+" < "$file" | paste -sd+ - | bc)
  • sed的(或grep的)提取并仅打印数
  • 糊使像字符串number + number + number-d+是分隔符)
  • bc做计算

或Perl

sum=$(perl -slanE '$s+=$F[1] if /^$id/}{say $s' -- -id="$id" "$file")
sum=$(ID="CallTilEdb" perl -lanE '$s+=$F[1] if /^$ENV{ID}/}{say $s' "$file")


Answer 4:

AWK翻译脚本:

#!/bin/bash
declare -t filename=hendelse.logg
declare -t occurance="$1"
declare -i sumTime=0

sumtime=$(awk -v entry=$occurance '
                                   $1==entry{time+=$NF+0}
                                  END{print time+0}' $filename)


文章来源: Reading a file in a shell script and selecting a section of the line
标签: bash shell cut