使用awk从两个文件中添加列

Adding columns from two file with awk

我有以下问题:

假设我有两个具有以下结构的文件:

 1   17.650  0.001  0.000E+00
 1   17.660  0.002  0.000E+00
 1   17.670  0.003  0.000E+00
 1   17.680  0.004  0.000E+00
 1   17.690  0.001  0.000E+00
 1   17.700  0.000  0.000E+00
 1   17.710  0.004  0.000E+00
 1   17.720  0.089  0.000E+00
 1   17.730  0.011  0.000E+00
 1   17.740  0.000  0.000E+00
 1   17.750  0.032  0.000E+00
 1   17.760  0.100  0.000E+00
 1   17.770  0.020  0.000E+00
 1   17.780  0.002  0.000E+00
                             
 2  -20.000  0.001  0.000E+00
 2  -19.990  0.002  0.000E+00
 2  -19.980  0.003  0.000E+00
 2  -19.970  0.004  0.000E+00
 2  -19.960  0.001  0.000E+00
 2  -19.950  0.000  0.000E+00
 2  -19.940  0.004  0.000E+00
 2  -19.930  0.089  0.000E+00
 2  -19.920  0.011  0.000E+00
 2  -19.910  0.000  0.000E+00
 2  -19.900  0.032  0.000E+00
 2  -19.890  0.100  0.000E+00
 2  -19.880  0.020  0.000E+00
 2  -19.870  0.002  0.000E+00

两个文件的前两列相同,不同的是第 3 列和第 4 列。以上是这些文件的示例。该空行是必不可少的,可以在将数据分成“块”的整个文件中找到。它必须存在!

使用以下命令:

awk '{a[FNR]=; b[FNR]=; s[FNR]+=} END{for (i=1; i<=FNR; i++) print a[i], b[i], s[i]}' file1 file2 > file-result

我正在尝试创建一个文件,其中第 1 列和第 2 列与原始文件中的列相同,第 3 列是 file1 和 file2 中第 3 列的总和。

如果没有空行,此命令有效。使用空白行我得到以下内容:

 1   17.650  0.001
 1   17.660  0.002
 1   17.670  0.003
 1   17.680  0.004
 1   17.690  0.001
 1   17.700  0.000
 1   17.710  0.004
 1   17.720  0.089
 1   17.730  0.011
 1   17.740  0.000
 1   17.750  0.032
 1   17.760  0.100
 1   17.770  0.020
 1   17.780  0.002
             0    
 2  -20.000  0.001
 2  -19.990  0.002
 2  -19.980  0.003
 2  -19.970  0.004
 2  -19.960  0.001
 2  -19.950  0.000
 2  -19.940  0.004
 2  -19.930  0.089
 2  -19.920  0.011
 2  -19.910  0.000
 2  -19.900  0.032
 2  -19.890  0.100
 2  -19.880  0.020
 2  -19.870  0.002

(请注意,在上面的第 3 列中我没有写出实际金额,但你明白了)

如何确保0不出现在空行中?想不通了。

请注意,如果前 2 列确实相同,则无需将它们存储在数组中;仅存储第一个文件的第 3 列。

您的问题的解决方案很简单:在处理第二个文件时测试该行是否为空白,如果是,则打印它。否则打印修改后的行。 next声明使所有这些变得非常简单和干净。

awk 'NR == FNR        {s[NR]=; next}
     /^[[:space:]]*$/ {print; next}
                      {print , , s[FNR]+}' file1 file2 > file-result

第一个块 运行 仅在第一个文件的行中(NR == FNR 仅在那时为真)。它将第 3 个字段存储在数组 s 中,由行号索引。 next 语句立即移动到下一行并阻止其他两个块到第一个文件的行上的 运行。

因此第二个块 运行 仅在第二个文件的行上,并且仅当它们为空白时(^[[:space:]]*$ 表示开头之间只有 0 个或更多空格(^)和行尾($))。该块按原样打印一个空行,next 语句再次立即移动到下一行,防止最后一个块到 运行。请注意,如果您的 awk 支持 \s 运算符,您可以将 [[:space:]] 替换为 \s。另请注意,测试也可以是 NF == 0NF 是当前记录的字段数)。

所以第三个和最后一个块 运行 仅在第二个文件的非空行上。它只是打印两个文件的前两个字段和第三个字段的总和(取自 </code> 和 <code>s 数组)。