【问题标题】:Add delimiters at end of each line在每行末尾添加分隔符
【发布时间】:2018-02-20 06:50:14
【问题描述】:

我有一个如下所示的 csv 文件。

id,id1,id2,id3,id4,id5
1,101,102,103,104
2,201,202,203
3,301,302

现在我想在每一行添加逗号(,)以使所有行具有相同数量的分隔符。所以期望的输出应该是。

id,id1,id2,id3,id4,id5
1,101,102,103,104,
2,201,202,203,,
3,301,302,,,

使用

awk -F "," ' { print NF-1 } ' file.csv | sort -r | head -1

我能够找到分隔符的最大出现次数,但不确定如何比较每一行并在小于最大值时附加逗号。

【问题讨论】:

    标签: awk sed


    【解决方案1】:

    使用GNU awk(因为我不知道这是否适用于其他实现)

    $ # simply assign value to NF
    $ awk -F, -v OFS=',' '{NF=6} 1' ip.txt
    id,id1,id2,id3,id4,id5
    1,101,102,103,104,
    2,201,202,203,,
    3,301,302,,,
    

    如果第一行确定所需字段的数量:

    $ awk -F, -v OFS=',' 'NR==1{f=NF} {NF=f} 1' ip.txt
    id,id1,id2,id3,id4,id5
    1,101,102,103,104,
    2,201,202,203,,
    3,301,302,,,
    

    如果任何一行确定最大字段:

    $ cat ip.txt 
    id,id1,id2
    1,101,102,103
    2,201,202,203,204
    3,301,302
    
    $ awk -F, -v OFS=',' 'NR==FNR{f=(!f || NF>f) ? NF : f; next} {NF=f} 1' ip.txt ip.txt
    id,id1,id2,,
    1,101,102,103,
    2,201,202,203,204
    3,301,302,,
    

    【讨论】:

      【解决方案2】:
      awk -F"," '{i=NF;c="";while (i++ < 6) {c=c","};print $0""c}' file
      

      输出:

      id,id1,id2,id3,id4,id5
      1,101,102,103,104,
      2,201,202,203,,
      3,301,302,,,
      

      【讨论】:

        【解决方案3】:

        您已经在使用变量NF,它表示一行中有多少个字段。

        awk -F , 'NF<6 { OFS=FS; for (i=NF+1; i<=6; i++) $i="" }1' filename
        

        我们从第一个未定义的字段开始循环并将其设置为空字符串,直到我们有六个字段。然后最后的1 负责打印现在已完全填充的行。 OFS=FS 是使输出字段分隔符也是逗号所必需的(默认为空格)。

        【讨论】:

          【解决方案4】:

          关注awk 也可能对您有所帮助。

          awk -F, '
          FNR==1{
            val=NF;
            print;
            next
          }
          {
            count=NF;
            while(count<val){
              value=value",";
              count++};
            print $0 value;
            value=count=""
          }
          '   Input_file
          

          输出如下:

          id,id1,id2,id3,id4,id5
          1,101,102,103,104,
          2,201,202,203,,
          3,301,302,,,
          

          【讨论】:

            【解决方案5】:

            统一 awk 方法(基于第一行 header 行的字段数):

            awk -F',' 'NR==1{ max_nf=NF; print }
                       NR>1{ printf "%s%.*s\n", $0, max_nf-NF, ",,,,,,,,," }' file
            

            输出:

            id,id1,id2,id3,id4,id5
            1,101,102,103,104,
            2,201,202,203,,
            3,301,302,,,
            

            或通过循环:

            awk -F',' 'NR==1{ max_nf=NF; print }
                       NR>1{ n=max_nf-NF; r=""; while (n--) r=r","; print $0 r }' file
            

            【讨论】:

            • 这可能比我的效率更高,因为您没有重写任何字段,但也许它有点晦涩。也许可以解释printf 宽度说明符如何决定实际打印多少个逗号?同样对于一个完全通用的解决方案,九个逗号的固定序列是不够的。
            猜你喜欢
            • 1970-01-01
            • 1970-01-01
            • 2012-02-24
            • 1970-01-01
            • 2015-02-16
            • 2013-04-05
            • 1970-01-01
            • 2018-04-15
            • 2017-04-28
            相关资源
            最近更新 更多