【问题标题】:AWK replace null column with the column value of next rowAWK用下一行的列值替换空列
【发布时间】:2016-02-05 23:11:09
【问题描述】:

我有以下示例文件,其中缺少列值,我想将其替换为同一列中的下一个可用值。

cat test.txt
11.2.0.1,ORA1,ORACLE
11.2.0.4,ORA2,ORACLE
11.2.0.3,ORA3,ORACLE
12.2.0.1,ORA4,ORACLE
,ORA5,ORACLE
,ORA6,ORACLE
12.2.0.2,ORA7,ORACLE
,MYS1,MYSQL
5.1,MYS2,MYSQL

这是我想要做的:

 cat test.txt |awk '{printf("%s,%s,%s\n", $11,$3,$1);}'|awk -F',' 'BEGIN{OFS=","}
   {
        for (i=1; i<=NF; i++)
        if ($i=="")
            --Read next column value
            --If next column is null, read futhur next
            -- Assign next available value to $i
        print
    }'

预期输出:

11.2.0.1,ORA1,ORACLE
11.2.0.4,ORA2,ORACLE
11.2.0.3,ORA3,ORACLE
12.2.0.1,ORA4,ORACLE
12.2.0.2,ORA5,ORACLE
12.2.0.2,ORA6,ORACLE
12.2.0.2,ORA7,ORACLE
5.1,MYS1,MYSQL
5.1,MYS2,MYSQL

谢谢

【问题讨论】:

    标签: shell awk


    【解决方案1】:

    你可以这样做:

    awk -F, '$1==""{a[n++]=$0;next} n{for (i=0;i<n;i++) print $1 a[i]; n=0} 1' file
    

    详情:

    $1=="" {          # if the first field is empty
        a[n++]=$0     # store the whole line at index n and increment n
        next          # jump to the next line
    }
    
    n {                    # if n isn't zero
        for (i=0;i<n;i++)  # loop over stored lines indexes
            print $1 a[i]  # and print lines starting with the current first field
        n=0                # set n to 0
    }
    
    1  # true, print the current line
    

    【讨论】:

      【解决方案2】:

      awk:

      tac file | awk -F, '$1{l=$1} !$1{$1=l} OFS=","' | tac
      
      • tac 类似于 cat,但逐行反转文件。
      • awk -F, 将字段分隔符设置为逗号。
      • $1{l=$1} 如果设置了第一个字段$1,则设置l 变量并打印该行
      • !$1{$1=l} 如果第一个字段 $1 未设置,则从 l 变量中获取值并打印该行。
      • OFS="," 将输出字段分隔符设置为逗号。
      • tac终于把文件反转回来了。

      输出:

      11.2.0.1,ORA1,ORACLE
      11.2.0.4,ORA2,ORACLE
      11.2.0.3,ORA3,ORACLE
      12.2.0.1,ORA4,ORACLE
      12.2.0.2,ORA5,ORACLE
      12.2.0.2,ORA6,ORACLE
      12.2.0.2,ORA7,ORACLE
      5.1,MYS1,MYSQL
      5.1,MYS2,MYSQL
      

      【讨论】:

      • 如果 $1 有一个 awk 决定用数值计算为零的值,那将失败。您需要测试$1!=""$1==""。如果您有 2 个必须具有相同值的变量(在这种情况下为 FSOFS),请不要在脚本的两端将它们独立设置为该值,在使用它们之前将它们一起设置在前面:awk 'BEGIN{FS=OFS=","}...。永远不要使用l(字母el)作为变量名,因为它看起来太像1(数字one),在某些字体中无法区分,因此会混淆您的代码。
      猜你喜欢
      • 1970-01-01
      • 2016-07-19
      • 2016-07-20
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-06-27
      • 2015-01-07
      相关资源
      最近更新 更多