web-dev-qa-db-fra.com

Lire le fichier HDF5 dans un tableau numpy

J'ai le code suivant pour lire un fichier hdf5 sous forme de tableau numpy:

hf = h5py.File('path/to/file', 'r')
n1 = hf.get('dataset_name')
n2 = np.array(n1)

et quand j’imprime n2 j’obtiens ceci: 

Out[15]:
array([[<HDF5 object reference>, <HDF5 object reference>,
        <HDF5 object reference>, <HDF5 object reference>...

Comment puis-je lire le HDF5 object reference pour afficher les données qui y sont stockées?

4
e9e9s

HDF5 a un modèle objet simple pour stocker datasets (en gros, l'équivalent d'un "tableau de fichiers") et les organiser en groupes (pensez aux répertoires). En plus de ces deux types d'objets, il existe des fonctionnalités beaucoup plus puissantes qui nécessitent des couches de compréhension.

Celui qui est à portée de main est un " Référence ". C'est une adresse interne dans le modèle de stockage de HDF5.

h5py fera tout le travail pour vous sans faire appel à des routines obscures, car il essaie de suivre autant que possible une interface de type dictée (mais pour les références, il est un peu plus complexe de la rendre transparente).

L'endroit à rechercher dans la documentation est Références d'objet et de région . Il indique que pour accéder à un objet désigné par la référence ref, vous devez

 my_object = my_file[ref]

Dans vos problèmes, il y a deux étapes: 1. Obtenez la référence 2. Obtenir le jeu de données

# Open the file
hf = h5py.File('path/to/file', 'r')
# Obtain the dataset of references
n1 = hf['dataset_name']
# Obtain the dataset pointed to by the first reference
ds = hf[n1[0]]
# Obtain the data in ds
data = ds[:]

Si le jeu de données contenant des références est en 2D, par exemple, vous devez utiliser

ds = hf[n1[0,0]]

Si le jeu de données est scalaire, vous devez utiliser

data = ds[()]

Pour obtenir tous les jeux de données à la fois:

all_data = [hf[ref] for ref in n1[:]]

en supposant un jeu de données 1D pour n1. Pour la 2D, l’idée tient, mais je ne vois pas de moyen court pour l’écrire.

Pour avoir une idée complète de la procédure d’aller-retour des données avec des références, j’ai écrit «programme d’écriture» et un «programme de lecture»:

import numpy as np
import h5py

# Open file                                                                                    
myfile = h5py.File('myfile.hdf5', 'w')

# Create dataset                                                                               
ds_0 = myfile.create_dataset('dataset_0', data=np.arange(10))
ds_1 = myfile.create_dataset('dataset_1', data=9-np.arange(10))

# Create a data                                                                                
ref_dtype = h5py.special_dtype(ref=h5py.Reference)

ds_refs = myfile.create_dataset('ref_to_dataset', shape=(2,), dtype=ref_dtype)

ds_refs[0] = ds_0.ref
ds_refs[1] = ds_1.ref

myfile.close()

et

import numpy as np
import h5py

# Open file                                                                                    
myfile = h5py.File('myfile.hdf5', 'r')

# Read the references                                                                          
ref_to_ds_0 = myfile['ref_to_dataset'][0]
ref_to_ds_1 = myfile['ref_to_dataset'][1]

# Read the dataset                                                                             
ds_0 = myfile[ref_to_ds_0]
ds_1 = myfile[ref_to_ds_1]

# Read the value in the dataset                                                                
data_0 = ds_0[:]
data_1 = ds_1[:]

myfile.close()

print(data_0)
print(data_1)

Vous remarquerez que vous ne pouvez pas utiliser la syntaxe NumPy standard, simple et pratique, pour les jeux de données de référence. En effet, les références HDF5 ne sont pas représentables avec les types de données NumPy. Ils doivent être lus et écrits un à la fois.

2
Pierre de Buyl

h5py fournit une méthode intrinsèque pour de telles tâches: read_direct()

hf = h5py.File('path/to/file', 'r')
n1 = np.zeros(shape, dtype=numpy_type)
hf['dataset_name'].read_direct(n1)
hf.close()

Les étapes combinées sont toujours plus rapides que n1 = np.array(hf['dataset_name']) si vous %timeit. Le seul inconvénient est qu'il est nécessaire de connaître au préalable la forme du jeu de données, qui peut être attribué en tant qu'attribut par le fournisseur de données.

2
ArcherEX

Voici une approche directe pour lire le fichier hdf5 sous forme de tableau numpy:

import numpy as np
import h5py

hf = h5py.File('path/to/file.h5', 'r')
n1 = np.array(hf["dataset_name"][:]) #dataset_name is same as hdf5 object name 

print(n1)
1
spate

Bonjour, c’est comme cela que je lis les données hdf5, en espérant que cela puisse vous être utile

with h5py.File('name-of-file.h5', 'r') as hf:
    data = hf['name-of-dataset'][:]
0