【问题标题】:Numpy savetxt with mixed data带有混合数据的 Numpy savetxt
【发布时间】:2019-04-10 16:11:42
【问题描述】:

我必须将包含字符串的数组保存为第一列,并将一些整数/浮点数保存为其余列。我试过了

rows = ['a', 'b', 'c']
value = np.random.rand(3,3)
np.savetxt('out.csv', np.c_[rows, value], fmt='%s %.2f %.2f %.2f')

但导致错误

TypeError: Mismatch between array dtype ('|S32') and format specifier ('%s %.2f %.2f %.2f')

我可以用numpy.savetxt 做到这一点吗?

PS:以下代码有效,但我不能限制位数。

np.savetxt('out.csv', np.c_[rows, value], fmt='%s')

上述命令的输出是

a 0.20196028482097483 0.5926321104002011 0.3249535106614311
b 0.061901131792619135 0.2124539226474711 0.7246679538084769
c 0.8459228604109359 0.1808180141813832 0.6723417117192844

我需要的输出是

a 0.20 0.59 0.32
b 0.06 0.21 0.72
c 0.85 0.18 0.67

【问题讨论】:

    标签: python numpy formatting typeerror


    【解决方案1】:

    numpy 数组只能有 1 个 dtype。因为您的第一列是一个字符串,所以您的整个数组都被转换为一个字符串。因此您不能使用%.2f,而是可以像这样使用%.4s

    np.savetxt('out.csv', np.c_[rows, value], fmt='%s %.4s %.4s %.4s')
    

    【讨论】:

      【解决方案2】:

      查看您要保存的内容:

      In [457]: arr = np.c_[rows, value]
      In [458]: arr
      Out[458]: 
      array([['a', '0.5798052037530684', '0.340056048668929',
              '0.9826015148933265'],
             ['b', '0.686642341561269', '0.22840250256173122',
              '0.874930037338561'],
             ['c', '0.38991473280876576', '0.1744123512308029',
              '0.7399608481535285']], dtype='<U32')
      

      通过这个简单的列堆叠,您已经创建了一个字符串数组。唯一可以格式化的方法是使用%s

      您需要创建一个结构化数组:

      为此,我可以创建一个元组列表和适当的 dtype。

      我的第一次尝试是干净的,但是 savetxt 无法更好地处理嵌套列表:

      In [460]: arr = np.array(list(zip(rows, value)), 'U3,3f')
      In [461]: arr
      Out[461]: 
      array([('a', [0.5798052 , 0.34005606, 0.9826015 ]),
             ('b', [0.68664235, 0.2284025 , 0.87493   ]),
             ('c', [0.38991472, 0.17441235, 0.73996085])],
            dtype=[('f0', '<U3'), ('f1', '<f4', (3,))])
      

      相反,我们需要为每个浮点值设置单独的字段:

      In [462]: arr = np.array(list(zip(rows, *value)), 'U3,f,f,f')
      In [463]: arr
      Out[463]: 
      array([('a', 0.5798052 , 0.68664235, 0.38991472),
             ('b', 0.34005606, 0.2284025 , 0.17441235),
             ('c', 0.9826015 , 0.87493   , 0.73996085)],
            dtype=[('f0', '<U3'), ('f1', '<f4'), ('f2', '<f4'), ('f3', '<f4')])
      

      现在我们可以使用您的fmt

      In [464]: np.savetxt('test.txt', arr, fmt='%s %.2f %.2f %.2f')
      In [465]: cat test.txt
      a 0.58 0.69 0.39
      b 0.34 0.23 0.17
      c 0.98 0.87 0.74
      

      糟糕 - 这已经转置了 value 数组 - 我应该使用:

      arr = np.array(list(zip(rows, *value.T)), 'U3,f,f,f')
      

      另一种选择是创建一个对象 dtype 数组:

      In [466]: M = np.zeros((3,4),object)
      In [467]: M[:,0] = rows
      In [468]: M[:,1:] = value
      In [469]: M
      Out[469]: 
      array([['a', 0.5798052037530684, 0.340056048668929, 0.9826015148933265],
             ['b', 0.686642341561269, 0.22840250256173122, 0.874930037338561],
             ['c', 0.38991473280876576, 0.1744123512308029, 0.7399608481535285]],
            dtype=object)
      In [470]: np.savetxt('test.txt', M, fmt='%s %.2f %.2f %.2f')
      In [471]: cat test.txt
      a 0.58 0.34 0.98
      b 0.69 0.23 0.87
      c 0.39 0.17 0.74
      

      【讨论】:

        猜你喜欢
        • 2014-02-07
        • 1970-01-01
        • 2017-04-05
        • 2023-04-05
        • 1970-01-01
        • 2018-12-02
        • 1970-01-01
        • 2017-06-21
        • 2018-09-03
        相关资源
        最近更新 更多