2016-03-17 52 views
0

这里是我的test_data.csv:蟒蛇 - numpy的:读CSV与正确的值类型numpy的

A,1,2,3,4,5 
B,6,7,8,9,10 
C,11,12,13,14,15 
A,16,17,18,19,20 

,我使用下面的代码读给一个numpy的数组:

def readCSVToNumpyArray(dataset): 
    with open(dataset) as f: 
     values = [i for i in csv.reader(f)] 

    data = numpy.array(values) 

    return data 

在主代码,我有:

numpyArray = readCSVToNumpyArray('test_data.csv') 
    print(numpyArray) 

这使我的输出:

(array([['A', '1', '2', '3', '4', '5'], 
     ['B', '6', '7', '8', '9', '10'], 
     ['C', '11', '12', '13', '14', '15'], 
     ['A', '16', '17', '18', '19', '20']], 
     dtype='|S2')) 

但是,所有的数字数组中被视为string,有没有让他们存储为float不通过每个元素去并指定类型的好办法?

谢谢!

+0

'numpy.ndarrays'是同质的。这是他们改进性能的原因之一。也许你可以有两个单独的数组,一个用于数字,另一个用于字符串?或者是一个字符串和数组数组的列表?否则,您需要查看[numpy records](http://docs.scipy.org/doc/numpy-dev/reference/generated/numpy.core.records.fromfile.html)或其他一些数据结构。你有没有考虑过熊猫数据框? –

+0

看一看[pandas](http://pandas.pydata.org/pandas-docs/stable/io.html#io-read-csv-table),它非常适合加载csv。你可以通过'asarray(table)'方便地将pandas表('DataFrame'实际)转换为numpy数组。 –

+0

如果你不想涉及一个额外的包(熊猫),请注意,'np.fromfile'或'np.genfromtxt'也是阅读文本文件的好工具,在你的情况下你必须定义一个数据类型并且通过它对这些功能。去看看他们的文档字符串,并看看'np.dtype'。 –

回答

1

由于每行的第一个字符是一个字符串,所以你必须在numpy中使用一个更灵活的类型,叫做“object”。使用此功能尝试,看看如果这是你在找什么:

def readCSVToNumpyArray(dataset): 
     values = [[]] 
     with open(dataset) as f: 
      counter = 0 
      for i in csv.reader(f): 
       for j in i: 
        try: 
         values[counter].append(float(j)) 
        except ValueError: 
         values[counter].append(j) 
       counter = counter + 1 
       values.append([]) 

     data = numpy.array(values[:-1],dtype='object') 

     return data 

    numpyArray = readCSVToNumpyArray('test_data.csv') 
    print(numpyArray) 

的结果是:

[['A' 1.0 2.0 3.0 4.0 5.0] 
    ['B' 6.0 7.0 8.0 9.0 10.0] 
    ['C' 11.0 12.0 13.0 14.0 15.0] 
    ['A' 16.0 17.0 18.0 19.0 20.0]] 
0

np.genfromtxt可以方便地将数据加载到一个结构数组。这将是一个一维数组,为每列一个字段:

模拟文件与行的列表:

In [265]: txt=b"""A,1,2,3,4,5 
     .....: B,6,7,8,9,10 
     .....: C,11,12,13,14,15 
     .....: A,16,17,18,19,20""" 
    In [266]: txt=txt.splitlines() 
    In [267]: A=np.genfromtxt(txt,delimiter=',',names=None,dtype=None) 
    In [268]: A 
    Out[268]: 
    array([(b'A', 1, 2, 3, 4, 5), (b'B', 6, 7, 8, 9, 10), 
      (b'C', 11, 12, 13, 14, 15), (b'A', 16, 17, 18, 19, 20)], 
      dtype=[('f0', 'S1'), ('f1', '<i4'), ('f2', '<i4'), ('f3', '<i4'), ('f4', '<i4'), ('f5', '<i4')]) 

它推断出来自列值dtype - 串和整数。字段由名称

In [269]: A['f0'] 
Out[269]: 
array([b'A', b'B', b'C', b'A'], 
     dtype='|S1') 
In [270]: A['f1'] 
Out[270]: array([ 1, 6, 11, 16]) 

访问我还可以定义一个dtype那将投入串在一个领域,其他领域的所有其他值。

In [271]: A=np.genfromtxt(txt,delimiter=',',names=None,dtype='S2,(5)int') 
In [272]: A 
Out[272]: 
array([(b'A', [1, 2, 3, 4, 5]), (b'B', [6, 7, 8, 9, 10]), 
     (b'C', [11, 12, 13, 14, 15]), (b'A', [16, 17, 18, 19, 20])], 
     dtype=[('f0', 'S2'), ('f1', '<i4', (5,))]) 
In [273]: A['f1'] 
Out[273]: 
array([[ 1, 2, 3, 4, 5], 
     [ 6, 7, 8, 9, 10], 
     [11, 12, 13, 14, 15], 
     [16, 17, 18, 19, 20]]) 
1

我会在使用熊猫阅读它,它可以让你很容易地设置每列的dtype。

import numpy as np 
import pandas as pd 

pdDF = pd.read_csv(
    'test_data.csv', 
    header=None, 
    names=list('abcdef'), 
    dtype=dict(zip(list('abcdef'),[str]+[float]*5))) 

现在每列都会有适当的dtype。

pdDF.b 
Out[24]: 
0  1 
1  6 
2 11 
3 16 
Name: b, dtype: float64 

如果你仍然希望它在numpy数组中,你可以只取值。

npArr = pdDF.values 

npArr 
Out[27]: 
array([['A', 1.0, 2.0, 3.0, 4.0, 5.0], 
     ['B', 6.0, 7.0, 8.0, 9.0, 10.0], 
     ['C', 11.0, 12.0, 13.0, 14.0, 15.0], 
     ['A', 16.0, 17.0, 18.0, 19.0, 20.0]], dtype=object) 

它仍然将是对“行”数组的对象,因为你不能让“A”变成浮动,但可根据需要单独的值将是浮动。

type(npArr[0,1]) 
Out[28]: float 

最后,如果你只想float数组,这也是很容易...只是吐出所有,但第一列作为一个数组,这将有D型:浮动,而不是对象。

pdDF.loc[:,pdDF.columns>='b'].values 
Out[28]: 
array([[ 1., 2., 3., 4., 5.], 
     [ 6., 7., 8., 9., 10.], 
     [ 11., 12., 13., 14., 15.], 
     [ 16., 17., 18., 19., 20.]]) 

pdDF.loc[:,pdDF.columns>='b'].values.dtype 
Out[29]: dtype('float64')