【问题标题】:Print the file name after summing a column in the file对文件中的一列求和后打印文件名
【发布时间】:2017-07-26 16:10:55
【问题描述】:

我正在使用 bash,并且我有一个目录,其中包含一堆看起来像这样的文件:

$ cat myFile.txt
 128 foo bar baz
4891 cat dog
  36 fish cat
 942 potato pants
 ...

我想创建这样的输出:

myFile.txt 5194
another.txt 4920
...

等等。我知道如何对文件求和:

cat myFile.txt | awk '{print $1}' | paste -sd+ - | bc

但我不知道如何重新打印文件名。特别是,我希望能够在事先不知道文件名的情况下做到这一点,如下所示:

cat *.txt | awk '{print $1}' | paste -sd+ - | bc | ... something here?

【问题讨论】:

  • 不确定如何从 myFile.txt 获得 5194。第1列的总数是5997
  • @hek2mgl 简单:我举了一个例子,用随机输入的数字来表示格式,而不是具体的值,因为我已经口头说过我想要一个总和。
  • Imo 预期输出应该与示例输入匹配。
  • @hek2mgl 当然,为什么不 - 我为那些敏感的人修复了它=)

标签: linux bash shell file


【解决方案1】:

你可以使用这个for循环:

for f in *.txt: do
   awk '{sum+=$1} END{print FILENAME, sum}' "$f"
done

awk 中的print 语句将打印输入文件名和总和。

【讨论】:

  • 完美,谢谢。我不知道 awk 中的 FILENAME,但我怀疑有 类似的东西。
【解决方案2】:

使用awk

awk 'function p(){if(pf)print pf,s;s=0}FNR==1{p()}{s+=$1;pf=FILENAME}END{p()}' *.txt

更好的可读性

awk '
       function p(){
           if(pf)print pf,s;
           s=0
       }
       FNR==1{
               p()
       }
       {
           s+=$1;
           pf=FILENAME
       }
       END{
            p()
       }
    ' *.txt

测试结果

[akshay@localhost tmp]$ ls *.txt
f1.txt  f2.txt

[akshay@localhost tmp]$ cat f1.txt 
1
2
3

[akshay@localhost tmp]$ cat f2.txt 
128
1
2

[akshay@localhost tmp]$ awk 'function p(){if(pf)print pf,s;s=0}FNR==1{p()}{s+=$1; pf=FILENAME}END{p()}' *.txt
f1.txt 6
f2.txt 131

【讨论】:

  • 甚至这个awk 'function p(){print pf,s;s=0}NR!=FNR && FNR==1{p()}{s+=$1; pf=FILENAME}END{p()}' *.txt
猜你喜欢
  • 2012-10-14
  • 2017-04-18
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-10-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多