如何将多个 hdf5 文件合并为一个文件和数据集?

How to combine multiple hdf5 files into one file and dataset?

import h5py
import numpy as np

with h5py.File("myCardiac.hdf5", "w") as f:
    dset = f.create_dataset("mydataset", (100,), dtype = 'i')
    grp = f.create_group("G:/Brain Data/Brain_calgary/")

我试过这段代码来创建一个 hdf5 文件。一个文件夹中有50个hhdf5文件。我想将所有 50 个 hdf5 文件合并为一个 hdf5 文件数据集。

要合并 50 个 .h5 文件,每个文件都有一个名为 kspace 的数据集和形式 (24, 170, 218, 256) , 到一个大数据集中,使用此代码:

import h5py
import os

with h5py.File("myCardiac.hdf5", "w") as f_dst:
    h5files = [f for f in os.listdir() if f.endswith(".h5")]

    dset = f_dst.create_dataset("mydataset", shape=(len(h5files), 24, 170, 218, 256), dtype='f4')

    for i, filename in enumerate(h5files):
        with h5py.File(filename) as f_src:
            dset[i] = f_src["kspace"]

详细说明

首先,您必须创建一个目标文件myCardiac.hdf5。然后获取目录下所有.h5文件的列表:

h5files = [f for f in os.listdir() if f.endswith(".h5")]

注意: os.listdir() 不带参数获取当前工作目录中 files/foldes 的列表。我希望此 python 脚本与文件位于同一目录中,并且 CWD 将设置到此目录。

下一步是在目标文件中创建具有所需大小和数据类型的数据集:

dset = f_dst.create_dataset("mydataset", shape=(len(h5files), 24, 170, 218, 256), dtype='f4')

然后您可以迭代地将数据从源文件复制到目标数据集。

for i, filename in enumerate(h5files):
    with h5py.File(filename) as f_src:
        dset[i] = f_src["kspace"]

另一种方法是使用 HDF5 虚拟数据集 在不复制数据的情况下在新文件中获得组合视图。 h5py reference here. Example below is adapted from a previous answer. See: 。此过程的注意事项:

  1. 代码中的注释记录了大部分步骤。
  2. 我使用 glob.glob() 获取源文件名列表 使用通配符(假设源文件被命名为:myCardiac_01.hdf5, myCardiac_02.hdf5, myCardiac_03.hdf5, etc)。
  3. 访问第一个源文件以获取数据类型和形状。所有源文件的值必须相同。
  4. 最后一步打印一些任意数据切片以演示基于源 shape=(24,170,218,256) 的行为。针对其他数据源进行适当修改。

源代码如下:

import h5py
import glob

h5_files = glob.glob('myCardiac_0?.hdf5')

# Get parameters from source files to define virtual layout and dataset
a0 = len(h5_files)
with h5py.File(h5_files[0],'r') as h5f:
    h5_dtype = h5f['kspace'].dtype
    h5_shape = h5f['kspace'].shape
    print(h5_dtype,h5_shape)
    
# Assemble virtual dataset
vs_layout = h5py.VirtualLayout(shape=((a0,)+h5_shape), dtype=h5_dtype)
for n, h5file in enumerate(h5_files):
    vs_layout[n] = h5py.VirtualSource(h5file, 'kspace', shape=h5_shape)

# Add virtual dataset to output file
with h5py.File('myCardiac_VDS.h5', 'w') as f:
    f.create_virtual_dataset('kspace_vdata', vs_layout)

# print some data slices from the virtual dataset
with h5py.File('myCardiac_VDS.h5', 'r') as f:
    vds_ds = f['kspace_vdata']
    print(vds_ds.dtype,vds_ds.shape)
    for i in range(vds_ds.shape[0]):
        print(f'Slice from file {i}:\n{vds_ds[i,:,0,0,0]}')