Skip to content

Commit

Permalink
Enhance HDF5 dataset reading function with improved error handling
Browse files Browse the repository at this point in the history
  • Loading branch information
dimitrivlachos committed Jan 28, 2025
1 parent 97361a9 commit e6b14bc
Showing 1 changed file with 70 additions and 25 deletions.
95 changes: 70 additions & 25 deletions include/dx2/h5/h5read_processed.h
Original file line number Diff line number Diff line change
Expand Up @@ -7,34 +7,79 @@
#include <string>
#include <vector>

/**
* @brief Reads a dataset from an HDF5 file into an std::vector.
*
* @tparam T The type of data to read (e.g., int, double).
* @param filename The path to the HDF5 file.
* @param dataset_name The name of the dataset to read.
* @return A std::vector containing the data from the dataset.
* @throws std::runtime_error If the file, dataset, or datatype cannot be opened
* or read.
*/
template <typename T>
std::vector<T> read_array_from_h5_file(std::string filename,
std::string array_name) {
std::vector<T> read_array_from_h5_file(const std::string &filename,
const std::string &dataset_name) {
// Start measuring time
auto start_time = std::chrono::high_resolution_clock::now();

// Open the HDF5 file
hid_t file = H5Fopen(filename.c_str(), H5F_ACC_RDONLY, H5P_DEFAULT);
if (file < 0) {
std::cout << "Error: Unable to open " << filename.c_str()
<< " as a hdf5 reflection table" << std::endl;
std::exit(1);
throw std::runtime_error("Error: Unable to open file: " + filename);
}

hid_t dataset = H5Dopen(file, array_name.c_str(), H5P_DEFAULT);
hid_t datatype = H5Dget_type(dataset);
size_t datatype_size = H5Tget_size(datatype);
assert((datatype_size == sizeof(T)));
hid_t dataspace = H5Dget_space(dataset);
size_t num_elements = H5Sget_simple_extent_npoints(dataspace);
hid_t space = H5Dget_space(dataset);
std::vector<T> data_out(num_elements);

H5Dread(dataset, datatype, H5S_ALL, space, H5P_DEFAULT, &data_out[0]);
float total_time = std::chrono::duration_cast<std::chrono::duration<double>>(
std::chrono::high_resolution_clock::now() - start_time)
.count();
std::cout << "READ TIME for " << array_name << " : " << total_time << "s"
<< std::endl;

H5Dclose(dataset);
H5Fclose(file);
return data_out;
}
try {
// Open the dataset
hid_t dataset = H5Dopen(file, dataset_name.c_str(), H5P_DEFAULT);
if (dataset < 0) {
throw std::runtime_error("Error: Unable to open dataset: " +
dataset_name);
}

try {
// Get the datatype and check size
hid_t datatype = H5Dget_type(dataset);
size_t datatype_size = H5Tget_size(datatype);
if (datatype_size != sizeof(T)) {
throw std::runtime_error(
"Error: Dataset type size does not match expected type size.");
}

// Get the dataspace and the number of elements
hid_t dataspace = H5Dget_space(dataset);
size_t num_elements = H5Sget_simple_extent_npoints(dataspace);

// Allocate a vector to hold the data
std::vector<T> data_out(num_elements);

// Read the data into the vector
herr_t status = H5Dread(dataset, datatype, H5S_ALL, H5S_ALL, H5P_DEFAULT,
data_out.data());
if (status < 0) {
throw std::runtime_error("Error: Unable to read dataset: " +
dataset_name);
}

// Close the dataset and return the data
H5Dclose(dataset);
H5Fclose(file);

// Log timing
auto end_time = std::chrono::high_resolution_clock::now();
double elapsed_time =
std::chrono::duration<double>(end_time - start_time).count();
std::cout << "READ TIME for " << dataset_name << " : " << elapsed_time
<< "s" << std::endl;

return data_out;

} catch (...) {
H5Dclose(dataset); // Ensure dataset is closed in case of failure
throw;
}
} catch (...) {
H5Fclose(file); // Ensure file is closed in case of failure
throw;
}
}

0 comments on commit e6b14bc

Please sign in to comment.