我正在尝试使用 awk 读取格式化文件。内容如下所示:
1PS1 A1 1 11.197 5.497 7.783
1PS1 A1 1 11.189 5.846 7.700
.
.
.
遵循c格式,这些行的格式如下 “%5d%5s%5s%5d%8.3f%.3f%8.3f” 其中,前 5 个位置是整数 (1),接下来 5 个位置是字符 (PS1),接下来 5 个位置是字符 (A1),接下来 5 个位置是整数 (1),接下来 24 个位置分为 3 列,每列 8 个位置3 位小数点 float 。
我一直在使用的只是使用“$1、$2、$3”来调用由列分隔的这些行。例如,
cat test.gro | awk 'BEGIN{i=0} {MolID[i]=$1; id[i]=$2; num[i]=$3; x[i]=$4;
y[i]=$5; z[i]=$6; i++} END { ...} >test1.gro
但是我遇到了一些问题,现在我尝试以上面讨论的格式化方式读取这些文件。
知道我该怎么做吗?
最佳答案
查看您的示例输入,格式字符串实际上似乎是 "%5d%-5s%5s%5d%8.3f%.3f%8.3f"
,其中第一个字符串字段被保留-有道理的。遗憾的是 awk 没有 scanf()
函数,但您可以通过几次 substr()
调用来获取数据
awk -v OFS=: '
{
a=substr($0,1,5)
b=substr($0,6,5)
c=substr($0,11,5)
d=substr($0,16,5)
e=substr($0,21,8)
f=substr($0,29,8)
g=substr($0,37,8)
print a,b,c,d,e,f,g
}
'
输出
1:PS1 : A1: 1: 11.197: 5.497: 7.783
1:PS1 : A1: 1: 11.189: 5.846: 7.700
如果您有 GNU awk,则可以使用 FIELDWIDTHS
变量,如下所示:
gawk -v FIELDWIDTHS="5 5 5 5 8 8 8" -v OFS=: '{print $1, $2, $3, $4, $5, $6, $7}'
还输出
1:PS1 : A1: 1: 11.197: 5.497: 7.783
1:PS1 : A1: 1: 11.189: 5.846: 7.700
关于scripting - 使用 awk 格式化读取,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9752157/