我从数据集中得到一个大型(类型化)数组,第一列包含用于索引每一行的唯一键,其他列包含已知大小的矩阵或向量。我有什么标准的方法或库可以有效地将其转换为哈希图,以便进行基于键的检索?将行拆分为单独的键值对象似乎并不十分节省内存。
这是基准次优解决方案:
arr = np.array([
('b0263', 'a', 1, 2, 3),
('26ab0', 'b', 4, 5, 6),
('6d7fc', 'c', 7, 8, 9),
('48a24', 'd', 0, 1, 2),
('1dcca', 'e', 3, 4, 5)],
dtype="S5, c, i4, i4, i4")
out = {key: values for key, *values in arr}
我想过一个字典,其中包含相应行的整数索引,但是它需要两个索引级别。
答案 0 :(得分:0)
您的结构化数组:
In [317]: arr
Out[317]:
array([(b'b0263', b'a', 1, 2, 3), (b'26ab0', b'b', 4, 5, 6),
(b'6d7fc', b'c', 7, 8, 9), (b'48a24', b'd', 0, 1, 2),
(b'1dcca', b'e', 3, 4, 5)],
dtype=[('f0', 'S5'), ('f1', 'S1'), ('f2', '<i4'), ('f3', '<i4'), ('f4', '<i4')])
第一个字段:
In [318]: arr['f0']
Out[318]: array([b'b0263', b'26ab0', b'6d7fc', b'48a24', b'1dcca'], dtype='|S5')
从该数组构建的字典:
In [321]: dd = {k:v for k,v in zip(arr['f0'], arr)}
In [322]: dd
Out[322]:
{b'b0263': (b'b0263', b'a', 1, 2, 3),
b'26ab0': (b'26ab0', b'b', 4, 5, 6),
b'6d7fc': (b'6d7fc', b'c', 7, 8, 9),
b'48a24': (b'48a24', b'd', 0, 1, 2),
b'1dcca': (b'1dcca', b'e', 3, 4, 5)}
In [323]: dd[b'6d7fc']
Out[323]: (b'6d7fc', b'c', 7, 8, 9)
在这种结构中,字典元素的值是原始数组的元素。
它具有type
np.void
和dtype
:
In [329]: dd[b'6d7fc'].dtype
Out[329]: dtype([('f0', 'S5'), ('f1', 'S1'), ('f2', '<i4'), ('f3', '<i4'), ('f4', '<i4')])
它实际上是原始文件的view
(我检查过__array_interface__
)。因此,除了指针/引用外,它不会消耗太多额外的内存。
最近的numpy
版本正在重新构造结构化数组的视图/副本,因此细节可能已经更改,尤其是在多字段引用方面。
我应该限定记忆注释。在此示例中,itemsize
只有18。但是arr[0]
引用数组的元素会创建一个新的np.void
对象。我怀疑对象开销大于18个字节。
您可以使用元组值创建字典:
In [335]: dd = {k:v.tolist()[1:] for k,v in zip(arr['f0'], arr)}
In [336]: dd[b'b0263']
Out[336]: (b'a', 1, 2, 3)