读取一个完整的数据文件并将数字舍入到小数点后2位并以相同的格式保存

Read a complete data file and round numbers to 2 decimal places and save it with the same format

我正在努力学习 python,我打算缩小一个非常大的数据文件,然后用 R 做一些统计分析。我需要阅读数据文件(见下文):

SCALAR
ND    3
ST  0
TS        10.00
0.0000
0.0000
0.0000
SCALAR
ND    3
ST  0
TS      3600.47
255.1744
255.0201
255.2748
SCALAR
ND    3
ST  0
TS      7200.42
255.5984
255.4946
255.7014

求出小数点后两位四舍五入,求最大数,把数字放在TS前面。最后以相同格式保存数据文件,如下所示:

SCALAR
ND    3
ST  0
TS        10.00
0.00
0.00
0.00
SCALAR
ND    3
ST  0
TS      3600.47
255.17
255.02
255.27
SCALAR
ND    3
ST  0
TS**MAX**      7200.42
255.60
255.49
255.70

我写过这样的代码:

import numpy as np
import matplotlib.pyplot as plt
import pickle

# Open file
f = open('data.txt', 'r')
thefile = open('output.txt', 'wb')
# Read and ignore header lines
header1 = f.readline()
header2 = f.readline()
header3 = f.readline()
header4 = f.readline()
data = []
for line in f:
    line = line.strip()
    columns = line.split()
    source = {}
    source['WSP'] = columns[0]
    #source['timestep'] = float(columns[1])
    source['timestep'] = columns[1]
    data.append(source)

f.close()

但是无法读取TS前面的数字。我想对数字进行四舍五入,但我使用的浮点数不起作用。之后我想把它放在一个循环中任何建议,我写代码的方式好吗?我将非常感谢您的帮助。

尝试"%.2f" % float(columns[1])四舍五入到小数点后两位。请注意,它给你的是一个字符串,而不是一个浮点数。我不明白你问的其他内容。

>>> "%.2f" % 255.5984
'255.60'

代码未正确执行(选择最大数量或保存到输出或...), 请把固定的, 但如果你只有 float 函数有问题,你可以选择 %.2f 或 round(num,2)

以下是如何使用 format 语法(新的 python2/3 格式语法)将一些浮点数转换为具有 2 位小数的字符串:

"{:.2f}".format(some_float)

关于您的其余问题:您的代码似乎没有正确处理文本文件的格式。您必须注意这样一个事实,即每一行都可以有:只有文本、文本和一个数字或只有一个数字。您可以通过尝试将每一行转换为浮点数来解决这个问题,如果失败则忽略它:

out=[]
for column in columns : 
    try:
        out.append("{:.2f}".format(float(column)))
    except ValueError:
        out.append(column)

如果可以假设需要舍入的浮点数本身仅出现在行上,那么第一部分就很容易完成。这不包括以字母字符为前缀的行,例如TS 3600.47.

from __future__ import print_function

with open('data.txt') as f, open('output.txt', 'w') as outfile:
    for line in (l.rstrip() for l in f):
        try:
            print('{:.2f}'.format(float(line)), file=outfile)
        except ValueError:
            print(line, file=outfile)

然而,第二部分要求整个文件被缓冲,因为不知道 TS 的最大值在哪里——它可能在文件的开头,在结束,或介于两者之间的任何地方。这是执行此操作的一些代码:

from __future__ import print_function

with open('data.txt') as f, open('output.txt', 'w') as outfile:
    lines = []
    max_ts = 0
    max_ts_idx = None

    for i, line in enumerate(l.rstrip() for l in f):
        try:
            lines.append('{:.2f}'.format(float(line)))
        except ValueError:
            if line.startswith('TS'):
                new_ts = float(line.split()[-1])
                if new_ts > max_ts:
                    max_ts = new_ts
                    max_ts_idx = i
            lines.append(line)

    for i, line in enumerate(lines):
        if i == max_ts_idx:
            line = line.replace('TS', 'TS**MAX**')
        print(line, file=outfile)

它与上面的纯打印版本基本相同,但是,行现在累积到列表中lines。 "TS" 行的最大值保存在 max_ts 中,"TS" 行的相应行号保存在 max_ts_idx 中。最后遍历 lines 列表并将行写入文件。如果该行包含 "TS" 的最大值(由 max_ts_idx 确定),则该行装饰有 **MAX**.