【问题标题】:how to print awk output horizontal in linux如何在linux中水平打印awk输出
【发布时间】:2020-11-30 05:43:52
【问题描述】:

我有一个脚本可以 greps 一些文件并打印 value ,但它是垂直的,如下所示

size=190000
date=1603278566981
repo-name=testupload
repo-path=/home/test/testupload
size=140000
date=1603278566981
repo-name=testupload2
repo-path=/home/test/testupload2
size=170000
date=1603278566981
repo-name=testupload3
repo-path=/home/test/testupload3

我希望这应该打印如下

size    date            repo-name          repo-path
190000  1603278566981   testupload      /home/test/testupload
140000  1603278566981   testupload2     /home/test/testupload2
170000  1603278566981   testupload3     /home/test/testupload3

我尝试了以下类似的方法,但它不起作用

无论如何我都可以用下面的格式化方式水平打印它

size    date            repo-name          repo-path
190000  1603278566981   testupload      /home/test/testupload
140000  1603278566981   testupload2     /home/test/testupload2
170000  1603278566981   testupload3     /home/test/testupload3

请建议和帮助

【问题讨论】:

    标签: linux bash shell awk sed


    【解决方案1】:

    您能否尝试在 GNU awk 中使用所示示例进行跟踪、编写和测试。

    awk '
    BEGIN{ FS="=" }
    /^size/{
      if(++count1==1){ header=$1 }
      sizeArr[++count]=$NF
      next
    }
    /^date/{
      if(++count2==1){ header=header OFS $1 }
      dateArr[count]=$NF
      next
    }
    /^repo-name/{
      if(++count3==1){ header=header OFS $1 }
      repoNameArr[count]=$NF
      next
    }
    /^repo-path/{
      if(++count4==1){ header=header OFS $1 }
      repopathArr[count]=$NF
      next
    }
    END{
      print header
      for(i=1;i<=count;i++){
        printf("%s %s %s %s\n",sizeArr[i],dateArr[i],repoNameArr[i],repopathArr[i])
      }
    }
    ' Input_file | column -t
    

    说明:为上述添加详细说明。

    awk '                                        ##Starting awk program from here.
    BEGIN{ FS="=" }                              ##Starting BEGIN section from here and setting field separator as = here.
    /^size/{                                     ##If line starts from size then do following.
      if(++count1==1){ header=$1 }               ##Checking if count1 variable is 1 then setting 1st field value as header.
      sizeArr[++count]=$NF                       ##Creating sizeArr with increasing count with 1 as an index and value is last field.
      next                                       ##next will skip all further statements.
    }
    /^date/{                                     ##If line starts from date then do
      if(++count2==1){ header=header OFS $1 }    ##Checking if count2 variable is 1 then setting 1st field value as header.
      dateArr[count]=$NF                         ##Creating dateArr with count as an index and value is last field.
      next                                       ##next will skip all further statements.
    }
    /^repo-name/{                                ##If line starts from repo-name then do
      if(++count3==1){ header=header OFS $1 }    ##Checking if count3 variable is 1 then setting 1st field value as header.
      repoNameArr[count]=$NF                     ##Creating repoNameArr with count as an index and value is last field.
      next                                       ##next will skip all further statements.
    }
    /^repo-path/{                                ##If line starts from repo-path then do
      if(++count4==1){ header=header OFS $1 }    ##Checking if count4 variable is 1 then setting 1st field value as header.
      repopathArr[count]=$NF                     ##Creating repopathArr with count as an index and value is last field.
      next                                       ##next will skip all further statements.
    }
    END{                                         ##Starting END block of this program from here.
      print header                               ##Printing header here.
      for(i=1;i<=count;i++){                     ##Starting loop from 1 to value of count.
        printf("%s %s %s %s\n",sizeArr[i],dateArr[i],repoNameArr[i],repopathArr[i]) ##Printing all array values here with index as i here.
      }
    }
    ' Input_file | column -t                     ##mentioning Input_file name and sendig awk output to column command for better looks.
    

    【讨论】:

      【解决方案2】:

      假设输入字段序列是恒定的,这里是 mawk 版本 1.3.4 的版本:

      awk -v RS='size=' -v OFS='\t' '
      BEGIN{ fmt = "%s" OFS "%s" OFS "%s" OFS" %s" ORS }
      function h(s) { return substr(s,1,index(s,"=")-1) }
      function v(s) { return substr(s,1+index(s,"=")) }
      NF{ if (!hdr++)
              printf(fmt,h(RS),h($2),h($3),h($4))
          printf(fmt,$1,v($2),v($3),v($4))
      }
      ' data | column -t
      

      ...虽然使用RS='(^|\n)size=' 并相应地编辑第一个标题属性会更安全。

      输出:

      size    date           repo-name    repo-path
      190000  1603278566981  testupload   /home/test/testupload
      140000  1603278566981  testupload2  /home/test/testupload2
      170000  1603278566981  testupload3  /home/test/testupload3
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2018-12-15
        • 1970-01-01
        相关资源
        最近更新 更多