使用h5py写文件的最快方法

1 投票
3 回答
5298 浏览
提问于 2025-04-18 11:14

首先,我看了一个主题,标题是“用Python写hdf5文件的最快方法是什么?”,但对我帮助不大。

我正在尝试加载一个大约1GB的文件(一个大小为(70133351,1)的矩阵),它是以h5f5结构存储的。

代码写得很简单,但运行得很慢。

import h5py
f = h5py.File("8.hdf5", "w")
dset = f.create_dataset("8", (70133351,1))

myfile=open("8.txt")

for line in myfile:
   line=line.split("\t")
   dset[line[1]]=line[0]

myfile.close()
f.close()

我还有一个50MB的小版本矩阵,我用同样的代码去处理它,结果24小时都没完成。

我知道要加快速度,最好的办法是避免使用“for循环”。如果我用的是普通的Python,我会用哈希推导式来处理。不过,看起来在这里不太适用。

我可以通过以下方式查询文件:

f = h5py.File("8.hdf5")
h=f['8']
print 'GFXVG' in h.attrs 

这会告诉我“True”,因为GFXVG是h中的一个键。

有没有人有什么想法呢?

这是文件的一部分示例:

508 LREGASKW
592 SVFKINKS
1151        LGHWTVSP
131 EAGQIISE
198 ELDDSARE
344 SQAVAVAN
336 ELDDSARF
592 SVFKINKL
638 SVFKINKI
107 PRTGAGQH
107 PRTGAAAA

谢谢

3 个回答

0

我最后选择使用一个叫做shelve的库(在Python中使用Pickle和shelve存储大型字典)来把一个很大的字典存到文件里。花了我两天时间才把这个字典写进文件,但一旦完成,我就可以很快加载和访问里面的任何元素。最终,我不需要每次都去读那个大文件,也不需要把所有信息都写到哈希里,直接就能做我想做的事情。

问题解决了!

0

既然它只有一GB,为什么不先把它完全加载到内存中呢?注意,看起来你在用一个str作为索引去访问数据集,这可能就是问题所在。

我刚意识到我之前理解错了问题,抱歉。看起来你的代码试图用索引1,这似乎是一个字符串,来作为索引?也许这里有个拼写错误?

import h5py
from numpy import zeros

data = zeros((70133351,1), dtype='|S8') # assuming your strings are all 8 characters, use object if vlen

with open('8.txt') as myfile: 
   for line in myfile:
       idx, item = line.strip().split("\t")
       data[int(line[0])] = line[1]

with h5py.File('8.hdf5', 'w') as f:
    dset = f.create_dataset("8", (70133351, 1), data=data)
1

你可以用 loadtext 把所有数据加载到一个 numpy array 中,然后用这个数组来创建你的 hdf5 数据集。

import h5py
import numpy as np

d = np.loadtxt('data.txt', dtype='|S18')

这会返回

array([['508.fna', 'LREGASKW'],
   ['592.fna', 'SVFKINKS'],
   ['1151.fna', 'LGHWTVSP'],
   ['131.fna', 'EAGQIISE'],
   ['198.fna', 'ELDDSARE'],
   ['344.fna', 'SQAVAVAN'],
   ['336.fna', 'ELDDSARF'],
   ['592.fna', 'SVFKINKL'],
   ['638.fna', 'SVFKINKI'],
   ['107.fna', 'PRTGAGQH'],
   ['1197.fna', 'ELDDSARR'],
   ['1309.fna', 'SQTIYVWF'],
   ['974.fna', 'PNNLRFIA'],
   ['230.fna', 'IGKVYHIE'],
   ['76.fna', 'PGVHSVWV'],
   ['928.fna', 'HERGGAND'],
   ['520.fna', 'VLKTDTTG'],
   ['1290.fna', 'EAALDLHR'],
   ['25.fna', 'FCSILGVV'],
   ['284.fna', 'YHKLTFED'],
   ['1110.fna', 'KITSSSDF']], 
  dtype='|S18')

然后

h = h5py.File('data.hdf5', 'w')
dset = h.create_dataset('data', data=d)

这会给出:

<HDF5 dataset "init": shape (21, 2), type "|S18">

撰写回答