【问题标题】:Convert import string to float with numpy's loadtext使用 numpy loadtxt 将导入字符串转换为浮点数
【发布时间】:2016-08-28 05:28:51
【问题描述】:

我正在尝试从平面文件中导入文本并将其转换为单行中的浮点值。我见过this post 有同样的错误,但我没有发现我的输入文件中哪些字符无效。还是我有语法错误?

作为字符串导入并打印结果:

data = np.loadtxt(file, delimiter='\t', dtype=str)
print(data[0:2])
... 
[["b'Time'" "b'Percent'"]
 ["b'99'" "b'0.067'"]]

尝试导入为浮点数:

# Import data as floats and skip the first row: data_float
data_float = np.loadtxt(data, delimiter='\t', dtype=float, skiprows=1)

它会抛出以下错误:

Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
    data_float = np.loadtxt(data, delimiter='\t', dtype=float, skiprows=1)
  File "<stdin>", line 848, in loadtxt
    items = [conv(val) for (conv, val) in zip(converters, vals)]
  File "<stdin>", line 848, in <listcomp>
    items = [conv(val) for (conv, val) in zip(converters, vals)]
ValueError: could not convert string to float: b'["b\'99\'" "b\'0.067\'"]'

顺便说一句,我还看到 this post 解释了 b 字符,但我认为这不是问题。

第一个答案建议的附加故障排除步骤:

data = np.loadtxt(file, delimiter="\tb'", dtype=str)

返回:

array(["b'Time\\tPercent'", "b'99\\t0.067'", "b'99\\t0.133'",
       "b'99\\t0.067'", "b'99\\t0'", "b'99\\t0'", "b'0\\t0.5'",
       "b'0\\t0.467'", "b'0\\t0.857'", "b'0\\t0.5'", "b'0\\t0.357'",
       "b'0\\t0.533'", "b'5\\t0.467'", "b'5\\t0.467'", "b'5\\t0.125'",
       "b'5\\t0.4'", "b'5\\t0.214'", "b'5\\t0.4'", "b'10\\t0.067'",
       "b'10\\t0.067'", "b'10\\t0.333'", "b'10\\t0.333'", "b'10\\t0.133'",
       "b'10\\t0.133'", "b'15\\t0.267'", "b'15\\t0.286'", "b'15\\t0.333'",
       "b'15\\t0.214'", "b'15\\t0'", "b'15\\t0'", "b'20\\t0.267'",
       "b'20\\t0.2'", "b'20\\t0.267'", "b'20\\t0.437'", "b'20\\t0.077'",
       "b'20\\t0.067'", "b'25\\t0.133'", "b'25\\t0.267'", "b'25\\t0.412'",
       "b'25\\t0'", "b'25\\t0.067'", "b'25\\t0.133'", "b'30\\t0'",
       "b'30\\t0.071'", "b'30\\t0'", "b'30\\t0.067'", "b'30\\t0.067'",
       "b'30\\t0.133'"], 
      dtype='<U16')

【问题讨论】:

    标签: python python-3.x ipython


    【解决方案1】:

    感谢所有关注我问题的人。我重新启动了 IPython,现在能够毫无问题地执行相同的代码。这是与上面相同的代码。

    data_float = np.loadtxt(file, delimiter='\t', dtype=float, skiprows=1)
    

    结果:

    In [1]: data_float
    Out[1]: 
    array([[  9.90000000e+01,   6.70000000e-02],
           [  9.90000000e+01,   1.33000000e-01],
           [  9.90000000e+01,   6.70000000e-02],
           [  9.90000000e+01,   0.00000000e+00],
           [  9.90000000e+01,   0.00000000e+00],
           [  0.00000000e+00,   5.00000000e-01],
           [  0.00000000e+00,   4.67000000e-01],
           [  0.00000000e+00,   8.57000000e-01],
           [  0.00000000e+00,   5.00000000e-01],
           [  0.00000000e+00,   3.57000000e-01],
           [  0.00000000e+00,   5.33000000e-01],
           [  5.00000000e+00,   4.67000000e-01],
           [  5.00000000e+00,   4.67000000e-01],
           [  5.00000000e+00,   1.25000000e-01],
           [  5.00000000e+00,   4.00000000e-01],
           [  5.00000000e+00,   2.14000000e-01],
           [  5.00000000e+00,   4.00000000e-01],
           [  1.00000000e+01,   6.70000000e-02],
           [  1.00000000e+01,   6.70000000e-02],
           [  1.00000000e+01,   3.33000000e-01],
           [  1.00000000e+01,   3.33000000e-01],
           [  1.00000000e+01,   1.33000000e-01],
           [  1.00000000e+01,   1.33000000e-01],
           [  1.50000000e+01,   2.67000000e-01],
           [  1.50000000e+01,   2.86000000e-01],
           [  1.50000000e+01,   3.33000000e-01],
           [  1.50000000e+01,   2.14000000e-01],
           [  1.50000000e+01,   0.00000000e+00],
           [  1.50000000e+01,   0.00000000e+00],
           [  2.00000000e+01,   2.67000000e-01],
           [  2.00000000e+01,   2.00000000e-01],
           [  2.00000000e+01,   2.67000000e-01],
           [  2.00000000e+01,   4.37000000e-01],
           [  2.00000000e+01,   7.70000000e-02],
           [  2.00000000e+01,   6.70000000e-02],
           [  2.50000000e+01,   1.33000000e-01],
           [  2.50000000e+01,   2.67000000e-01],
           [  2.50000000e+01,   4.12000000e-01],
           [  2.50000000e+01,   0.00000000e+00],
           [  2.50000000e+01,   6.70000000e-02],
           [  2.50000000e+01,   1.33000000e-01],
           [  3.00000000e+01,   0.00000000e+00],
           [  3.00000000e+01,   7.10000000e-02],
           [  3.00000000e+01,   0.00000000e+00],
           [  3.00000000e+01,   6.70000000e-02],
           [  3.00000000e+01,   6.70000000e-02],
           [  3.00000000e+01,   1.33000000e-01]])
    

    【讨论】:

    • 这是我在下面的评论。我很乐意删除它。但是你能先解释一下为什么吗?
    • 我现在解决了,请参阅我发布的答案。我也可以删除整个问题,因为答案很简单,但也许会对某人有所帮助。
    • 删除问题:题外话。来自 SO------关闭弹出窗口。这个问题是由无法再复制的问题或简单的印刷错误引起的。虽然类似的问题可能是这里的主题,但这个问题的解决方式不太可能帮助未来的读者。这通常可以通过在发布之前确定并仔细检查重现问题所需的最短程序来避免。
    • 解决问题的是skiprows=1,而不是重启。 genfromtxt 可用于将第一行视为标题。
    • 抱歉,我不明白你所说的skirows=1是什么意思。我以前也有过。感谢您提供有关genfromtxt 的提示。
    【解决方案2】:

    问题是你的数字被引用了。也就是说,该字段是'99',而不是99。有两种方法可以做到这一点。您可以提供去除引号并返回浮点数的转换器函数。或者您可以使用csv 模块来加载您的数据,然后将该数据传递给numpy

    使用转换器函数

    import numpy as np
    from io import StringIO
    
    data = """'x'\t'y'
    '1'\t'2.5'"""
    
    arr = np.loadtxt(StringIO(data), dtype=float, delimiter="\t", skiprows=1, 
        converters=dict.fromkeys([0, 1], (lambda s: float(s.strip(b"'"))))
    )
    

    使用csv

    import csv
    import numpy as np
    from io import StringIO
    
    data = """'x'\t'y'
    '1'\t'2.5'"""
    
    reader = csv.reader(StringIO(data), quotechar="'", delimiter="\t")
    next(reader) # skip headers
    arr = np.array(list(reader), dtype=float)
    

    在这两个示例中,我都使用了StringIO,因此您可以轻松查看“文件”的内容。您当然可以将文件名或文件对象传递给这些函数。

    【讨论】:

    • 我在阅读时得到 nans,我正在做 abcd = json.dumps("6.3, 2.7, 4.9, 1.8"); np.genfromtxt(StringIO(abcd), delimiter=',', dtype=float, converters=dict.fromkeys([0, 1], (lambda s: float(s.strip(b'"'))))).reshape(1,4) 返回 array([[6.3, 2.7, 4.9, nan]])
    【解决方案3】:

    你可以试试:

    data = np.loadtxt(file, delimiter="\tb'", dtype=str)
    

    表示实际的分隔符似乎包含字符“b”?

    【讨论】:

    • 这没有错误,但看起来不正确。我现在将补充问题。
    • >>>float(b'42') 不是问题,但是您正在处理的问题,>>>float("b'42'") 不是同一件事和错误出现 ValueError:无法将字符串转换为浮点数:“b'18'”
    • 刚刚更新了您的建议输出的问题。
    • 糟糕,我忘记了引号。回到你之前的分隔符,抱歉
    • 尝试使用 delimiter = '\t',并将以下所有字符串替换为空字符串: newstring = value.replace('"','').replace("b'"," ").replace("\\'",'') 我认为这应该可以将包含数字的值转换为浮点数。
    猜你喜欢
    • 2020-11-06
    • 1970-01-01
    • 2011-11-25
    • 2011-07-18
    • 2019-10-31
    • 2014-12-24
    • 2021-12-28
    • 2013-03-22
    • 1970-01-01
    相关资源
    最近更新 更多