我有一个以下文件(实际上,它具有更多的列和大量的行)
0 0 -39 36.093 14.981 3-0.71520 0.71520-0.16345 0.16345-0.67954-0.67954
0 0 -40 336.902 26.500 2-0.69704 0.69704-0.16844 0.16844-0.69696-0.69696
0 0 -41 37.034 15.869 5-0.67794 0.67794-0.17335 0.17335-0.71439-0.71439
0 0 -42 27.538 14.992 1-0.65776 0.65776-0.17833 0.17833-0.73181-0.73181
它是固定格式的文件。在第六列中,我有从1开始到5的数字(格式:I4)。在此特定列中,我需要替换1至20、2-> 21等,而所有其他条目均不受影响。在此示例中,它将产生如下内容:
0 0 -39 36.093 14.981 22-0.71520 0.71520-0.16345 0.16345-0.67954-0.67954
0 0 -40 336.902 26.500 21-0.69704 0.69704-0.16844 0.16844-0.69696-0.69696
0 0 -41 37.034 15.869 25-0.67794 0.67794-0.17335 0.17335-0.71439-0.71439
0 0 -42 27.538 14.992 20-0.65776 0.65776-0.17833 0.17833-0.73181-0.73181
我进入了论坛,但似乎没有一个解决方案完全符合我的情况。预先表示感谢。
这是该问题的附录。这是原始的单行(请注意空格):
0 0 -39 36.093 14.981 3-0.71520 0.71520-0.16345 0.16345-0.67954-0.67954 0 287.85 405.71 5.51 287.32 405.17 5.58 1.894 0.53 11.62 90.00 322.65 2 9561 2947 8902 1.67 1 1.000 536346150 -4 0.936 33.55 151.65 91.270 174.170 1
最后建议的解决方案是:
0 0 -39 36.093 14.981 23-0.71520 0.71520-0.16345 0.16345-0.67954-0.67954 0 287.85 405.71 5.51 287.32 405.17 5.58 1.894 0.53 11.62 90.00 322.65 2 9561 2947 8902 1.67 1 1.000 536346150 -4 0.936 33.55 151.65 91.270 174.170 1
答案 0 :(得分:0)
此awk
将第六列分为两部分,并由a[1]
和a[2]
表示。后来的第6列被分配了更新的值,其中a[1]
增加了20
。
awk '{split($6,a,"-");$6=a[1]+20"-"a[2]}1' inputfile
0 0 -39 36.093 14.981 23-0.71520 0.71520-0.16345 0.16345-0.67954-0.67954
0 0 -40 336.902 26.500 22-0.69704 0.69704-0.16844 0.16844-0.69696-0.69696
0 0 -41 37.034 15.869 25-0.67794 0.67794-0.17335 0.17335-0.71439-0.71439
0 0 -42 27.538 14.992 21-0.65776 0.65776-0.17833 0.17833-0.73181-0.73181
您可以选择使用OFS="\t"
获得更清晰的输出。或使用gsub
:
awk '{split($6,a,"-"); gsub($6,a[1]+20"-"a[2])}1' input
0 0 -39 36.093 14.981 23-0.71520 0.71520-0.16345 0.16345-0.67954-0.67954
0 0 -40 336.902 26.500 22-0.69704 0.69704-0.16844 0.16844-0.69696-0.69696
0 0 -41 37.034 15.869 25-0.67794 0.67794-0.17335 0.17335-0.71439-0.71439
0 0 -42 27.538 14.992 21-0.65776 0.65776-0.17833 0.17833-0.73181-0.73181
当输入文件为:
cat input
0 0 -39 36.093 14.981 3-0.71520 0.71520-0.16345 0.16345-0.67954-0.67954
0 0 -40 336.902 26.500 2-0.69704 0.69704-0.16844 0.16844-0.69696-0.69696
0 0 -41 37.034 15.869 5-0.67794 0.67794-0.17335 0.17335-0.71439-0.71439
0 0 -42 27.538 14.992 1-0.65776 0.65776-0.17833 0.17833-0.73181-0.73181
0 0 -39 36.093 14.981 3-0.71520 0.71520-0.16345 0.16345-0.67954-0.67954 0 287.85 405.71 5.51 287.32 405.17 5.58 1.894 0.53 11.62 90.00 322.65 2 9561 2947 8902 1.67 1 1.000 536346150 -4 0.936 33.55 151.65 91.270 174.170 1
awk 'NF{split($6,a,"-"); gsub($6,a[1]+20"-"a[2])}1' input
0 0 -39 36.093 14.981 23-0.71520 0.71520-0.16345 0.16345-0.67954-0.67954
0 0 -40 336.902 26.500 22-0.69704 0.69704-0.16844 0.16844-0.69696-0.69696
0 0 -41 37.034 15.869 25-0.67794 0.67794-0.17335 0.17335-0.71439-0.71439
0 0 -42 27.538 14.992 21-0.65776 0.65776-0.17833 0.17833-0.73181-0.73181
0 0 -39 36.093 14.981 23-0.71520 0.71520-0.16345 0.16345-0.67954-0.67954 0 287.85 405.71 5.51 287.32 405.17 5.58 1.894 0.53 11.62 90.00 322.65 2 9561 2947 8902 1.67 1 1.000 536346150 -4 0.936 33.55 151.65 91.270 174.170 1
答案 1 :(得分:0)
您提到您有一个带有特定输出的固定格式文件。
第6列的格式为I4
,它是Fortran格式说明符。
由于我们没有完整的格式,因此我执行了以下操作:
获取第5列的位置
$ awk '{match($0,$5); print RSTART+RLENGTH-1; exit}' file
28
这意味着列6从位置29开始,长度为4。 基于此数字,我们现在可以将每个文件分为3部分。长度为28的第一字符串,长度为4的第二字符串以及其余的第三字符串。我们在第二部分中添加20,并以相同的格式进行打印:
$ awk '{p1=substr($0,1,28); p2=substr($0,29,4); p3=substr($0,33)}
{ printf "%s%4d%s\n", p1,p2+20,p3}' file