Чтение массива неизвестной длины из файла HDF в Fortran

Я хочу прочитать массив размерности один произвольного размера из файла hdf. Я работаю над примером «Чтение/запись во внешний набор данных» здесь, но так как я заранее не знаю размеров массива, мне нужно вызвать несколько дополнительных подпрограмм.

Размер пространства данных можно найти, так как вывод m дает правильное значение, но сами данные не могут быть прочитаны.

Тестовый массив, который я пытаюсь прочитать, выглядит так:

HDF5 "test_1d.h5" {
GROUP "/" {
   DATASET "sample_array" {
      DATATYPE  H5T_IEEE_F64LE
      DATASPACE  SIMPLE { ( 5 ) / ( 5 ) }
      DATA {
      (0): 1, 4, 2, 8, 6
      }
   }
}
}

Программа:

program hdf_read_test

use hdf5
implicit none

     integer                                      :: m,hdferror
     character(len=1024)                          :: fname,dsetname
     double precision, dimension(:), allocatable  :: X

     integer(hid_t)                               :: file_id,dset_id,dspace_id
     integer(hsize_t), dimension(1)               :: dims,maxdims

     ! ------------------------------------------

     ! Specify filename/dataset name.
     fname = "test_1d.h5"
     dsetname = "sample_array"

     call h5fopen_f(fname, H5F_ACC_RDONLY_F, file_id, hdferror)
     call h5dopen_f(file_id, dsetname, dset_id, hdferror)

     ! ---------------
     ! Figure out the size of the array.

     ! Get the dataspace ID
     call h5dget_space_f(dset_id,dspace_id,hdferror)

     ! Getting dims from dataspace
     call h5sget_simple_extent_dims_f(dspace_id, dims, maxdims, hdferror)   

     ! Allocate memory for the array.
     m = dims(1)
     allocate(X(m))

     ! ----------------
     ! Read the array.
     call h5dread_f(dset_id, H5T_IEEE_F64LE, X, dims, hdferror, H5S_ALL_F, dspace_id)

     ! Check the values.
     write(*,*)
     write(*,*) "Array size: ",m
     write(*,*) "Array elements: ",X
     write(*,*)

     ! -----------------
     ! Clean up.
     deallocate(X)

     call h5sclose_f(dspace_id, hdferror)
     call h5dclose_f(dset_id, hdferror)
     call h5fclose_f(file_id, hdferror)
     call h5close_f(hdferror)

end program hdf_read_test

Скомпилировано через

h5fc -o hdf_read_test hdf_read_test.f90

производит вывод:

HDF5-DIAG: Error detected in HDF5 (1.8.11) thread 140545957812032:
  #000: ../../../src/H5Dio.c line 182 in H5Dread(): can't read data
    major: Dataset
    minor: Read failed
  #001: ../../../src/H5Dio.c line 438 in H5D__read(): unable to set up type info
    major: Dataset
    minor: Unable to initialize object
  #002: ../../../src/H5Dio.c line 914 in H5D__typeinfo_init(): not a datatype
    major: Invalid arguments to routine
    minor: Inappropriate type
HDF5-DIAG: Error detected in HDF5 (1.8.11) thread 140545957812032:
  #000: ../../../src/H5T.c line 1761 in H5Tclose(): not a datatype
    major: Invalid arguments to routine
    minor: Inappropriate type

Спасибо.


person moo    schedule 08.03.2016    source источник
comment
Я не вижу вызова h5open_f для инициализации библиотеки.   -  person IanH    schedule 08.03.2016
comment
В этом была проблема. Мои глаза обманывали меня, комбинируя h5open_f и h5fopen_f.   -  person moo    schedule 08.03.2016


Ответы (1)


Во-первых, ваша ошибка заключается в том, что с fortran API вам нужно вызывать h5open_f(hdferror) для инициализации библиотеки HDF перед вызовом h5fopen_f.

Боковые примечания.

  • Я бы проверял значение hdferror после каждого вызова HDF.
  • Вызов h5sget_simple_extent_dims_f() возвращает ранг в последнем аргументе (hdferror) или -1 в случае ошибки.
person Timothy Brown    schedule 08.03.2016
comment
Вот и все, спасибо. И я проверяю значение, я просто удалил их здесь для минимального примера. - person moo; 08.03.2016