如何在 C++ 中使用 HDF5 存储多个 2D 字符数组?

Posted

技术标签:

【中文标题】如何在 C++ 中使用 HDF5 存储多个 2D 字符数组?【英文标题】:How to store multiple 2D char arrays using HDF5 in C++? 【发布时间】:2020-03-31 15:20:17 【问题描述】:

我想将多个二维字符数组写入一个 HDF5 数据集。在下面的代码中,结构中有两个数组,我将(std::copy)“hello”s 放入一个数组(name),将“hi”s 放入另一个数组(nicknams)。我认为结果会是这样的:

(b'hello', b'hey')
(b'hello', b'hey')
(b'hello', b'hey')
(b'hello', b'hey')

但是当我实际运行代码时,结果是这样的:

(b'hello', b'hey')
(b'(\xae\nVD\xae\nV\xff\xff', b'\xdc\x82\nV\x12\xd2\xfcv\x8f\x01')
(b'\x04', b'\x01') 
(b'$\xf8O', b'9\x08\xd2\xd5\xb4\xf8O')]

由于第一行看起来不错,我猜想在将数组写入数据集时空字符有问题。我已经查看了官方网页上的示例代码(https://support.hdfgroup.org/HDF5/examples/),但我仍然不明白这个问题来自哪里。我想知道问题是什么以及如何解决。

#include "pch.h"
#include <iostream>
#include "H5Cpp.h"

using namespace H5;

const H5std_string MEMBER1("name");
const H5std_string MEMBER2("nickname");

struct newStruct1 
    char        name[4][10];
    char        nickname[4][10];
;


void struct_to_dataset(newStruct1 *ptr_struct)
        
    H5File file("file.h5", H5F_ACC_TRUNC);

    hid_t dtype_str = H5Tcopy(H5T_C_S1);
    size_t size = 10 * sizeof(char);                    
    H5Tset_size(dtype_str, size);

    hsize_t dim[] =  4 ;   
    DataSpace space(1, dim);

    CompType mtype1(sizeof(newStruct1));
    mtype1.insertMember(MEMBER1, HOFFSET(newStruct1, name), dtype_str);
    mtype1.insertMember(MEMBER2, HOFFSET(newStruct1, nickname), dtype_str);

    DataSet dataset = file.createDataSet("dset", mtype1, space);

    dataset.write(ptr_struct, mtype1);  


int main()

    newStruct1 struct01;
    newStruct1 *ptr01 = &struct01;

    char word1[10] =  "hello" ;
    char word2[10] =  "hey" ;

    for (int i = 0; i < 4; i++) 
        std::copy(word1, word1 + 10, ptr01->name[i]);
        std::copy(word2, word2 + 10, ptr01->nickname[i]);
    

    struct_to_dataset(ptr01);

【问题讨论】:

【参考方案1】:

请查看HDFql,因为它可以让您从处理 HDF5 复合数据集的低级细节中解脱出来。在 C++ 中使用 HDFql,您的问题可以解决如下:

// define structure
struct data

    char name[10];
    char nickname[10];
;

// declare variables
char script[1024];
struct data values[4];
int i;

// create an HDF5 file named "file.h5" and use (i.e. open) it
HDFql::execute("CREATE AND USE FILE file.h5");

// create a dataset named "dset" of data type compound of one dimension (size 4) composed of two members (name and nickname)
HDFql::execute("CREATE DATASET dset AS COMPOUND(name AS CHAR(10), nickname AS CHAR(10))(4)");

// populate variable "values"
for(i = 0; i < 4; i++)

    memcpy(values[i].name, "hello\0\0\0\0\0", 10);
    memcpy(values[i].nickname, "hey\0\0\0\0\0\0\0", 10);


// insert (i.e. write) values from variable "values" into dataset "dset"
sprintf(script, "INSERT INTO dset VALUES FROM MEMORY %d", HDFql::variableTransientRegister(values));
HDFql::execute(script);

有关如何使用 HDFql 的其他详细信息和示例,请参阅reference manual。

【讨论】:

以上是关于如何在 C++ 中使用 HDF5 存储多个 2D 字符数组?的主要内容,如果未能解决你的问题,请参考以下文章

将浮点数组写入和附加到 C++ 中 hdf5 文件中的唯一数据集

如何从 C++ 中的 hdf5 文件中读取数据块?

如何在 HDF5DotNet 中创建 2D H5Array

如何在 NumPy 中将 HDF5 2D 数组转换为 1D?

如何使用 C++ 库在 HDF5 中找出数据集的 PredType

如何在 C++ 中将 stl::string 写入 HDF5 文件