2012-07-24 95 views
2
创建HDF5布尔枚举

我创建了3个双打和一个boolen使用numpy数组和书面他们使用h5py到文件:如何阅读h5py用C

import numpy as np 
import h5py 

data = np.zeros(10, dtype=[("THETA",np.double),("PHI",np.double),("PSI",np. double),("FLAG",np.bool)]) 

with h5py.File("testout.h5") as f: 
    f.create_dataset("data", data=data) 

h5py为创建一个枚举类型布尔字段:

HDF5 "testout.h5" { 
GROUP "/" { 
    DATASET "data" { 
     DATATYPE H5T_COMPOUND { 
     H5T_IEEE_F64LE "THETA"; 
     H5T_IEEE_F64LE "PHI"; 
     H5T_IEEE_F64LE "PSI"; 
     H5T_ENUM { 
      H5T_STD_I8LE; 
      "FALSE"   0; 
      "TRUE"    1; 
     } "FLAG"; 
     } 
     DATASPACE SIMPLE { (10)/(10) } 
    } 
} 
} 

现在我需要阅读用C这个文件,事情就变得复杂:

typedef enum { 
    false = 0; 
    true 
} bool; 

typedef struct { 
    double THETA, PHI, PSI; 
    bool FLAG; 
} pointing_t; 

我不知道如何定义一个拥有枚举类型:

hid_t memtype = H5Tcreate (H5T_COMPOUND, sizeof(pointing_t)); 
H5Tinsert (memtype, "THETA", HOFFSET (pointing_t, THETA), H5T_NATIVE_DOUBLE); 
H5Tinsert (memtype, "PHI", HOFFSET (pointing_t, PHI), H5T_NATIVE_DOUBLE); 
H5Tinsert (memtype, "PSI", HOFFSET (pointing_t, PSI), H5T_NATIVE_DOUBLE); 
# this should be an ENUM!! 
H5Tinsert (memtype, "FLAG", HOFFSET (pointing_t, FLAG), H5T_NATIVE_DOUBLE); 

我粘贴要点一个完整的“不工作”的例子,试图读取与以往的Python代码片段创建HDF5文件:

http://gist.github.com/3168909

有人有建议吗? 谢谢!

回答

2

找到了解决办法,你需要在HDF5创建一个枚举类型:

#define CPTR(VAR,CONST) ((VAR)=(CONST),&(VAR)) 
hid_t boolenumtype = H5Tcreate(H5T_ENUM, sizeof(bool)); 
status = H5Tenum_insert(boolenumtype, "FALSE", CPTR(val, FALSE)); 
printf ("H5Tenum_insert (FALSE): %i\n", status); 
status = H5Tenum_insert(boolenumtype, "TRUE", CPTR(val, TRUE)); 
printf ("H5Tenum_insert (TRUE): %i\n", status); 

,然后将其添加到mem类型:

H5Tinsert (memtype, "FLAG", HOFFSET (pointing_t, FLAG), boolenumtype); 

在github的一例进行工作。

2

解决此问题的更简单方法是使用1字节无符号字符来存储布尔类型。在h5py,可以通过调用以下

import h5py 
import numpy as np 

# Generate some boolean data 

shape = (100, 100) 
data = np.zeros(shape, dtype=np.bool) 

# Save the boolean data as uchars 

f = h5py.File('foo.h5') 
dset = f.create_dataset('/bar', dtype='u1', shape=shape) 
dset[:] = data[:] 

在C/C++存储布尔阵列,就可以读取uchars成bool*阵列,并且它们将被正确地解释。这是因为它们是1字节,就像C/C++布尔值一样,并且任何非零位的内容在C/C++中被解释为true