【问题标题】:Error storing a hdf5 file with a list of strings存储带有字符串列表的 hdf5 文件时出错
【发布时间】:2020-05-28 22:48:36
【问题描述】:
def storeFlagsFile(FLAGS_F, file_name, t0, text, ID):
    if not FLAGS_F:  # this flag doesnt work for mulitple users
        f = h5py.File(file_name, "r+")
        data_content = np.array([np.round(time.time() - t0, 3), text])
        asciiList = np.array([str(n).encode("utf-8", "ignore") for n in data_content]).reshape(1, 2)
        dt = h5py.string_dtype(encoding='utf-8')
        dset = f[str(ID)].create_dataset('AcqFlags', data=asciiList, compression="gzip", chunks=True, maxshape=(None, 2), dtype=dt)
        FLAGS_F = 1
    else:
        f = h5py.File(file_name, "r+")        
        data_content = np.array([np.round(time.time() - t0, 3), text]) 
        asciiList = np.array([str(n).encode("utf-8", "ignore") for n in data_content]).reshape(1, 2)
        f[str(ID)+'/AcqFlags'].resize((f[str(ID)+'/AcqFlags'].shape[0] + 1), axis = 0)
        f[str(ID)+'/AcqFlags'][-1:] = asciiList

我想以 (None, 2) 格式保存这样的数据格式,因为我通过调用 storeFlagsFile 函数不断更新每行的数据行。

['4.412' 'a']
['5.412' 'b']
['6.412' 'c']
['8.226' 'd']

其中 t0 第一列和文本 = 数据的第二列,我将其作为每行的输入行提供给 storeFlagsFile(FLAGS_F, file_name, t0, text, ID)。 FLAGS_F 最初为 0,ID = "122"。

但我正在像这样观察 hdf5 文件:

谁能指出我做错了什么?谢谢!

【问题讨论】:

    标签: python hdf5


    【解决方案1】:

    不清楚(对我来说)为什么您没有在 AcqFlags 数据集中获得 2 个字段。我能够让您的代码段进行小的修改。 (我使用的是 h5py 2.9.0。在 h5py 2.10.0 中为可变长度字符串添加了一个新的 dtype。dt= 声明中的 cmets 会注意到这种变化。这不是代码中的错误。)见下文。

    import h5py, numpy as np
    import time
    
    def storeFlagsFile(FLAGS_F, file_name, t0, text, ID):
        if not FLAGS_F:  # this flag doesnt work for mulitple users
            with h5py.File(file_name, "r+") as f:
                data_content = np.array([np.round(time.time() - t0, 3), text])
                asciiList = np.array([str(n).encode("utf-8", "ignore") for n in data_content]).reshape(1, 2)
                #dt = h5py.string_dtype(encoding='utf-8') # for h5py 2.10.0
                dt = h5py.special_dtype(vlen=str)   # for h5py 2.9.0
                dset = f[str(ID)].create_dataset('AcqFlags', data=asciiList, compression="gzip", chunks=True, maxshape=(None, 2), dtype=dt)
                FLAGS_F = 1
        else:
            with h5py.File(file_name, "r+") as f:      
                data_content = np.array([np.round(time.time() - t0, 3), text]) 
                asciiList = np.array([str(n).encode("utf-8", "ignore") for n in data_content]).reshape(1, 2)
                f[str(ID)+'/AcqFlags'].resize((f[str(ID)+'/AcqFlags'].shape[0] + 1), axis = 0)
                f[str(ID)+'/AcqFlags'][-1:] = asciiList
    
    file_name = 'SO_62064344.h5'
    ID = 122
    with h5py.File(file_name, 'w') as f:
        f.create_group(str(ID))
    
    storeFlagsFile(False, file_name, 4.412, 'a', ID)       
    storeFlagsFile(True, file_name, 5.412, 'b', ID)       
    storeFlagsFile(True, file_name, 6.412, 'c', ID)       
    storeFlagsFile(True, file_name, 8.226, 'd', ID)     
    storeFlagsFile(True, file_name, 9.773, 'e', ID)  
    

    其他想法/观察:

    1. 我注意到您将时间值存储为字符串。那是你要的吗? HDF5 和 h5py 可以在每个字段/列中存储不同的数据类型,因此您可以根据需要混合浮点数和字符串。它需要不同的 dtype(如记录数组)。
    2. 您使用 FLAGS_F 作为标志来创建 AcqFlags 数据集。您可以简化它以测试是否存在,或使用require_dataset
    3. 您一次向可调整大小的数据集添加 1 行。这对于“小型”数据集是可以的,但如果您一次创建 10e6 行 1 行,则可能会出现性能问题。
    4. 如果您有兴趣,我回答了其他问题,这些问题显示了如何执行上述 #2 和 #3。您可能会发现以下答案之一很有帮助:

    【讨论】:

      猜你喜欢
      • 2020-12-06
      • 2014-06-06
      • 2020-05-26
      • 1970-01-01
      • 2017-12-29
      • 2016-08-02
      • 2016-10-18
      • 1970-01-01
      • 2010-10-20
      相关资源
      最近更新 更多