我想将文件中的所有数字截断到小数点后五位。例如,我有这个文件:
Ga O # 83645, Ga2O3
1.0
12.2348604202 0.0000000000 0.0000000000
0.0000000000 3.0320000648 0.0000000000
-1.3752052829 0.0000000000 5.6183021388
Ga O
8 12
Direct
0.590021042 0.500000000 0.794251030
0.409978979 0.500000000 0.205748985
0.909978943 0.000000000 0.205749006
0.090021023 -0.000000000 0.794251030
0.658887031 0.000000000 0.314083014
因此,我想要拥有相同的文件,但仅包含 5 位小数的数字。
答案1
如果您不介意将整数也转换为浮点数,则可以使用numfmt
:
$ numfmt --field=1- --format=%.5f --invalid=ignore < file
1.00000
12.23487 0.00000 0.00000
0.00000 3.03201 0.00000
-1.37521 0.00000 5.61831
Ga O
8.00000 12.00000
Direct
0.59003 0.50000 0.79426
0.40998 0.50000 0.20575
0.90998 0.00000 0.20575
0.09003 0.00000 0.79426
0.65889 0.00000 0.31409
解释
--field=1-
该选项告诉
numfmt
需要替换哪些出现的内容。1-
在本例中意味着从第一次出现直到行尾。--format=%.5f
此选项告诉
numfmt
如何格式化输出数字。%.5f
在本例中意味着将它们格式化为具有 5 位小数的浮点数。--invalid=ignore
该选项告诉
numfmt
当无法格式化数字时该怎么做。ignore
在这种情况下,只需忽略有问题的输入并继续下一个输入。
默认情况下,numfmt
应用IEEE 754 舍入规则- 如果您想要简单截断,可以添加--round=towards-zero
。舍入选项的完整列表是up
、down
、from-zero
(默认)、towards-zero
、nearest
。
您可以查看手册页以了解更多详细信息:
如果您想要 IEEE 754 舍入,但希望它严格应用于小数点后超过 5 位数字的浮点数,那么我建议使用perl
- 它可以匹配正则表达式,例如sed
,但允许您将sprintf
表达式应用于捕获的模式:
perl -pe 's/[+-]?\d*[.]\d{5,}/sprintf "%.5f", $&/ge' file
与 GNU 类似sed
,perl
可以通过添加选项来就地修改文件-i
。
答案2
您可以使用sed
:
sed -E 's/([0-9]+\.[0-9]{5})[0-9]*/\1/g' file
添加-i
选项以就地添加文件。
答案3
使用 GNU sed
:
sed -E 's/\.([0-9]{5})[0-9]*/.\1/g' file
输出:
1.0
12.23486 0.00000 0.00000
0.00000 3.03200 0.00000
-1.37520 0.00000 5.61830
Ga O
8 12
Direct
0.59002 0.50000 0.79425
0.40997 0.50000 0.20574
0.90997 0.00000 0.20574
0.09002 -0.00000 0.79425
0.65888 0.00000 0.31408
使用扩展正则表达式-E
:
sed -E
.<five digits><n digits>
用匹配图案。用\.([0-9]{5})[0-9]*
捕获点后面的 5 位数字.
([0-9]{5})
s/\.([0-9]{5})[0-9]*/
用点.
和捕获的模式替换匹配项:
/.\1/
答案4
使用 GNU awk
:
awk '{print gensub(/([0-9]+\.[0-9]{5})[0-9]*/, "\\1", "g")}' input_file > output_file
它使用awk
函数从给定文件 ( ) 中gensub
选择一个十进制数 ( ) ,并将其拆分为两部分。第一部分有 5 位小数 ( ),第二部分是十进制数的其余部分 ( )。/([0-9]+\.[0-9]{5})[0-9]*/
input_file
([0-9]+\.[0-9]{5})
[0-9]*
gensub
然后用其第一部分 ( ) 替换选定的数字,"\\1"
并对它可以找到的所有十进制数 ( "g"
)执行此操作input_file
。
然后,该命令将结果保存到输出文件(> output_file
)。