从两个列表python创建一个numpy.recarray

时间:2018-04-21 19:58:57

标签: arrays list numpy

是否有一种简单的方法可以从两个列表中创建numpy.recarray。例如,请提供以下列表:

list1 = ["a","b","c"]
list2 = [1,2,3,4,5,6,7,8,9,10,11,12]

我想要做的是获得以下结果:

rec_array = np.rec.array([('a', 1), ('a', 2),('a', 3),('a', 4),
                          ('b', 5), ('b', 6),('b', 7),('b', 8),
                          ('c', 9), ('c', 10),('c', 11),('c', 12)] dtype = [('string','|U5'),('int', '<i4')])

我的意思是我知道rec.array是如何工作的,但我真的不知道如何从列表中创建一个。从dicts选项开始,key ,value可能会让事情变得简单。但是从列表中有没有办法做到这一点?。

2 个答案:

答案 0 :(得分:1)

In [73]: list1 = ["a","b","c"]
    ...: list2 = [1,2,3,4,5,6,7,8,9,10,11,12]
    ...: 
In [74]: dt = [('string','|U5'),('int', '<i4')]

简单的元素配对:

In [75]: [(i,j) for i, j in zip(list1,list2)]
Out[75]: [('a', 1), ('b', 2), ('c', 3)]

list2分为3组:

In [79]: list3 = [list2[i:i+4] for i in range(0,12,4)]
In [80]: list3
Out[80]: [[1, 2, 3, 4], [5, 6, 7, 8], [9, 10, 11, 12]]

双重列表理解:

In [81]: [(i,j) for i,row in zip(list1,list3) for j in row]
Out[81]: 
[('a', 1),
 ('a', 2),
 ('a', 3),
 ('a', 4),
 ('b', 5),
 ('b', 6),
 ('b', 7),
 ('b', 8),
 ('c', 9),
 ('c', 10),
 ('c', 11),
 ('c', 12)]

从中创建一个结构化数组:

In [82]: np.array(_, dtype=dt)
Out[82]: 
array([('a',  1), ('a',  2), ('a',  3), ('a',  4), ('b',  5), ('b',  6),
       ('b',  7), ('b',  8), ('c',  9), ('c', 10), ('c', 11), ('c', 12)],
      dtype=[('string', '<U5'), ('int', '<i4')])

或制作(3,4)数组:

In [86]: [[(i,j) for j in row] for i,row in zip(list1, list3)]
Out[86]: 
[[('a', 1), ('a', 2), ('a', 3), ('a', 4)],
 [('b', 5), ('b', 6), ('b', 7), ('b', 8)],
 [('c', 9), ('c', 10), ('c', 11), ('c', 12)]]
In [87]: np.array(_, dt)
Out[87]: 
array([[('a',  1), ('a',  2), ('a',  3), ('a',  4)],
       [('b',  5), ('b',  6), ('b',  7), ('b',  8)],
       [('c',  9), ('c', 10), ('c', 11), ('c', 12)]],
      dtype=[('string', '<U5'), ('int', '<i4')])
In [88]: _.shape
Out[88]: (3, 4)

或将list1复制为与list2相同的尺寸:

In [97]: np.array([(i,j) for i,j in zip(np.repeat(list1,4),list2)],dt).reshape(3
    ...: ,4)
Out[97]: 
array([[('a',  1), ('a',  2), ('a',  3), ('a',  4)],
       [('b',  5), ('b',  6), ('b',  7), ('b',  8)],
       [('c',  9), ('c', 10), ('c', 11), ('c', 12)]],
      dtype=[('string', '<U5'), ('int', '<i4')])

答案 1 :(得分:1)

除了@ hpaulj的方法,您还可以分配然后填充数组:

dtype = [('string','|U5'),('int', '<i4')]
>>> list1 = ["a","b","c"]
>>> list2 = [1,2,3,4,5,6,7,8,9,10,11,12]
>>> 
>>> result = np.recarray((12,), dtype=dtype)
>>> result['string'].reshape(3, 4).T[...] = list1
>>> result['int'] = list2
>>> result
rec.array([('a',  1), ('a',  2), ('a',  3), ('a',  4), ('b',  5),
           ('b',  6), ('b',  7), ('b',  8), ('c',  9), ('c', 10),
           ('c', 11), ('c', 12)],
          dtype=[('string', '<U5'), ('int', '<i4')])

这里的(小)优势是可以在list1上使用广播。