h5geo 0.4.0
C++17 and python API to work with geo-data (seismic, wells, maps, other in process) based on HDF5. Aimed at geoscientists and developers.
Loading...
Searching...
No Matches
h5coreimpl.h
1#ifndef H5COREIMPL_H
2#define H5COREIMPL_H
3
4#include "h5enum.h"
5
6#include <type_traits>
7#include <string>
8#include <vector>
9#include <regex>
10
11#ifndef H5GT_USE_EIGEN
12#define H5GT_USE_EIGEN // should be defined before including h5gt
13#endif
14
15#include <Eigen/Dense>
16
17#include <h5gt/H5File.hpp>
18#include <h5gt/H5Group.hpp>
19#include <h5gt/H5DataSet.hpp>
20#include <h5gt/H5DataSpace.hpp>
21#include <h5gt/H5Attribute.hpp>
22
23#include <units/units.hpp>
24
25
26namespace h5geo
27{
28
29template<typename Object, typename T,
30 typename std::enable_if<
31 std::is_same<Object, h5gt::File>::value ||
32 std::is_same<Object, h5gt::Group>::value>::type*>
34 Object& node,
35 const std::string& datasetPath,
36 T* M,
37 size_t nH5Rows,
38 size_t nH5Cols,
39 const std::string& unitsFrom,
40 const std::string& unitsTo)
41{
42 if(datasetPath.empty() ||
43 !node.hasObject(datasetPath, h5gt::ObjectType::Dataset))
44 return false;
45
46 if (nH5Rows == 0 || nH5Cols == 0)
47 return false;
48
49 h5gt::DataSet dset = node.getDataSet(datasetPath);
50 if (!dset.getCreateProps().isChunked())
51 return false;
52
53 auto dtype = dset.getDataType();
54 if (!dtype.isTypeEqual(h5gt::AtomicType<T>())){
55 return false;
56 }
57
58 if (!unitsFrom.empty() && !unitsTo.empty()){
59 double coef = units::convert(
60 units::unit_from_string(unitsFrom),
61 units::unit_from_string(unitsTo));
62 for(size_t i = 0; i < nH5Rows*nH5Cols; i++)
63 M[i] *= coef;
64 }
65
66 try {
67 std::vector<size_t> dims = {nH5Rows, nH5Cols};
68 dset.resize(dims);
69 dset.write_raw(M);
70 return true;
71 } catch (h5gt::Exception e) {
72 return false;
73 }
74}
75
76template<typename Object, typename D,
77 typename std::enable_if<
78 (std::is_same<Object, h5gt::File>::value ||
79 std::is_same<Object, h5gt::Group>::value) &&
80 std::is_arithmetic<typename D::Scalar>::value>::type*>
82 Object& node,
83 const std::string& datasetPath,
84 Eigen::DenseBase<D>& M,
85 const std::string& unitsFrom,
86 const std::string& unitsTo)
87{
89 node, datasetPath, M.derived().data(), M.cols(), M.rows(), unitsFrom, unitsTo);
90}
91
92template<typename Object, typename T,
93 typename std::enable_if<
94 (std::is_same<Object, h5gt::File>::value ||
95 std::is_same<Object, h5gt::Group>::value) &&
96 std::is_arithmetic<T>::value>::type*>
98 Object& node,
99 const std::string& datasetPath,
100 std::vector<T>& v,
101 const std::string& unitsFrom,
102 const std::string& unitsTo)
103{
105 node, datasetPath, v.data(), 1, v.size(), unitsFrom, unitsTo);
106}
107
108template<typename Object, typename T,
109 typename std::enable_if<
110 (std::is_same<Object, h5gt::File>::value ||
111 std::is_same<Object, h5gt::Group>::value) &&
112 std::is_arithmetic<T>::value>::type*>
114 Object& node,
115 const std::string& datasetPath,
116 T& v,
117 const std::string& unitsFrom,
118 const std::string& unitsTo)
119{
121 node, datasetPath, &v, 1, 1, unitsFrom, unitsTo);
122}
123
124template<typename Object, typename T,
125 typename std::enable_if<
126 std::is_same<Object, h5gt::File>::value ||
127 std::is_same<Object, h5gt::Group>::value>::type*>
129 Object& node,
130 const std::string& datasetPath,
131 T* M,
132 size_t nH5Rows,
133 size_t nH5Cols,
134 const std::string& unitsFrom,
135 const std::string& unitsTo)
136{
137 if (datasetPath.empty())
138 return false;
139
140 if (nH5Rows == 0 || nH5Cols == 0)
141 return false;
142
143 if(node.hasObject(datasetPath, h5gt::ObjectType::Dataset)){
144 h5gt::DataSet dset = node.getDataSet(datasetPath);
145 auto dtype = dset.getDataType();
146 if (!dtype.isTypeEqual(h5gt::AtomicType<T>()) ||
147 dset.getMemSpace().getElementCount() != nH5Rows*nH5Cols){
148 node.unlink(datasetPath);
149 node.template createDataSet<T>(
150 datasetPath, h5gt::DataSpace({nH5Rows, nH5Cols}));
151 }
152 } else {
153 node.template createDataSet<T>(
154 datasetPath, h5gt::DataSpace({nH5Rows, nH5Cols}));
155 }
156
157 if (!unitsFrom.empty() && !unitsTo.empty()){
158 double coef = units::convert(
159 units::unit_from_string(unitsFrom),
160 units::unit_from_string(unitsTo));
161 for(size_t i = 0; i < nH5Rows*nH5Cols; i++)
162 M[i] *= coef;
163 }
164
165 node.getDataSet(datasetPath).write_raw(M);
166 return true;
167}
168
169
170template<typename Object, typename D,
171 typename std::enable_if<
172 (std::is_same<Object, h5gt::File>::value ||
173 std::is_same<Object, h5gt::Group>::value) &&
174 std::is_arithmetic<typename D::Scalar>::value>::type*>
176 Object& node,
177 const std::string& datasetPath,
178 Eigen::DenseBase<D>& M,
179 const std::string& unitsFrom,
180 const std::string& unitsTo)
181{
182 return _overwriteDataset(
183 node, datasetPath, M.derived().data(), M.cols(), M.rows(), unitsFrom, unitsTo);
184}
185
186template<typename Object, typename T,
187 typename std::enable_if<
188 (std::is_same<Object, h5gt::File>::value ||
189 std::is_same<Object, h5gt::Group>::value) &&
190 std::is_arithmetic<T>::value>::type*>
192 Object& node,
193 const std::string& datasetPath,
194 std::vector<T>& v,
195 const std::string& unitsFrom,
196 const std::string& unitsTo)
197{
198 return _overwriteDataset(
199 node, datasetPath, v.data(), 1, v.size(), unitsFrom, unitsTo);
200}
201
202template<typename Object, typename T,
203 typename std::enable_if<
204 (std::is_same<Object, h5gt::File>::value ||
205 std::is_same<Object, h5gt::Group>::value) &&
206 std::is_arithmetic<T>::value>::type*>
208 Object& node,
209 const std::string& datasetPath,
210 T& v,
211 const std::string& unitsFrom,
212 const std::string& unitsTo)
213{
214 return _overwriteDataset(
215 node, datasetPath, &v, 1, 1, unitsFrom, unitsTo);
216}
217
218template <typename Object, typename T,
219 typename std::enable_if<
220 std::is_same<Object, h5gt::File>::value ||
221 std::is_same<Object, h5gt::Group>::value>::type*>
222inline bool _readDataset(
223 Object& node,
224 const std::string& datasetPath,
225 T* M,
226 size_t nElem,
227 const std::string& unitsFrom,
228 const std::string& unitsTo)
229{
230 if (datasetPath.empty() ||
231 !node.hasObject(datasetPath, h5gt::ObjectType::Dataset))
232 return false;
233
234 if (nElem == 0)
235 return false;
236
237 h5gt::DataSet dset = node.getDataSet(datasetPath);
238 auto dtype = dset.getDataType();
239 if (!dtype.isTypeEqual(h5gt::AtomicType<T>()) ||
240 dset.getMemSpace().getElementCount() != nElem)
241 return false;
242
243 dset.read(M);
244
245 if (!unitsFrom.empty() && !unitsTo.empty()){
246 double coef = units::convert(
247 units::unit_from_string(unitsFrom),
248 units::unit_from_string(unitsTo));
249 for(size_t i = 0; i < nElem; i++)
250 M[i] *= coef;
251 }
252
253 return true;
254}
255
256template<typename Object, typename D,
257 typename std::enable_if<
258 (std::is_same<Object, h5gt::File>::value ||
259 std::is_same<Object, h5gt::Group>::value ||
260 std::is_same<Object, h5gt::DataSet>::value) &&
261 std::is_arithmetic<typename D::Scalar>::value>::type*>
262inline bool readDataset(
263 Object& node,
264 const std::string& datasetPath,
265 Eigen::DenseBase<D>& M,
266 const std::string& unitsFrom,
267 const std::string& unitsTo)
268{
269 // we don't want to resize vector if no data to read
270 if (datasetPath.empty() ||
271 !node.hasObject(datasetPath, h5gt::ObjectType::Dataset))
272 return false;
273
274 h5gt::DataSet dset = node.getDataSet(datasetPath);
275 auto dtype = dset.getDataType();
276 if (!dtype.isTypeEqual(h5gt::AtomicType<typename D::Scalar>()))
277 return false;
278
279 std::vector<size_t> dims = dset.getDimensions();
280 M.derived().resize(dims[1], dims[0]); // resize the derived object
281 return _readDataset(node, datasetPath, M.derived().data(), M.size(), unitsFrom, unitsTo);
282}
283
284template<typename Object,
285 typename std::enable_if<
286 std::is_same<Object, h5gt::File>::value ||
287 std::is_same<Object, h5gt::Group>::value ||
288 std::is_same<Object, h5gt::DataSet>::value>::type*>
289inline Eigen::MatrixXf readFloatEigenMtxDataset(
290 Object& node,
291 const std::string& datasetPath,
292 const std::string& unitsFrom,
293 const std::string& unitsTo)
294{
295 Eigen::MatrixXf M;
296 readDataset(node, datasetPath, M, unitsFrom, unitsTo);
297 return M;
298}
299
300template<typename Object,
301 typename std::enable_if<
302 std::is_same<Object, h5gt::File>::value ||
303 std::is_same<Object, h5gt::Group>::value ||
304 std::is_same<Object, h5gt::DataSet>::value>::type*>
305inline Eigen::MatrixXd readDoubleEigenMtxDataset(
306 Object& node,
307 const std::string& datasetPath,
308 const std::string& unitsFrom,
309 const std::string& unitsTo)
310{
311 Eigen::MatrixXd M;
312 readDataset(node, datasetPath, M, unitsFrom, unitsTo);
313 return M;
314}
315
316
317template <typename Object, typename T,
318 typename std::enable_if<
319 std::is_same<Object, h5gt::File>::value ||
320 std::is_same<Object, h5gt::Group>::value ||
321 std::is_same<Object, h5gt::DataSet>::value>::type*>
322inline bool _readAttribute(
323 Object& holder,
324 const std::string& attrName,
325 T *v,
326 size_t nElem,
327 const std::string& unitsFrom,
328 const std::string& unitsTo)
329{
330 if (attrName.empty() || !holder.hasAttribute(attrName))
331 return false;
332
333 if (nElem == 0)
334 return false;
335
336 h5gt::Attribute attr = holder.getAttribute(attrName);
337 auto dtype = attr.getDataType();
338 if (!dtype.isTypeEqual(h5gt::AtomicType<T>()) ||
339 attr.getMemSpace().getElementCount() != nElem)
340 return false;
341
342 attr.read(v);
343
344 if (!unitsFrom.empty() && !unitsTo.empty()){
345 double coef = units::convert(
346 units::unit_from_string(unitsFrom),
347 units::unit_from_string(unitsTo));
348 for(size_t i = 0; i < nElem; i++)
349 v[i] *= coef;
350 }
351
352 return true;
353}
354
355template<typename Object, typename D,
356 typename std::enable_if<
357 (std::is_same<Object, h5gt::File>::value ||
358 std::is_same<Object, h5gt::Group>::value ||
359 std::is_same<Object, h5gt::DataSet>::value) &&
360 std::is_arithmetic<typename D::Scalar>::value>::type*>
361inline bool readAttribute(
362 Object& holder,
363 const std::string& attrName,
364 Eigen::DenseBase<D> &v,
365 const std::string& unitsFrom,
366 const std::string& unitsTo)
367{
368 // we don't want to resize vector if no data to read
369 if (attrName.empty() || !holder.hasAttribute(attrName))
370 return false;
371
372 h5gt::Attribute attr = holder.getAttribute(attrName);
373 auto dtype = attr.getDataType();
374 if (!dtype.isTypeEqual(h5gt::AtomicType<typename D::Scalar>()))
375 return false;
376
377 v.derived().resize(holder.getAttribute(attrName).getMemSpace().getElementCount());
378 return _readAttribute(
379 holder, attrName, v.derived().data(), v.size(), unitsFrom, unitsTo);
380}
381
382template <typename Object, typename T,
383 typename std::enable_if<
384 (std::is_same<Object, h5gt::File>::value ||
385 std::is_same<Object, h5gt::Group>::value ||
386 std::is_same<Object, h5gt::DataSet>::value) &&
387 std::is_arithmetic<T>::value>::type*>
388inline bool readAttribute(
389 Object& holder,
390 const std::string& attrName,
391 std::vector<T> &v,
392 const std::string& unitsFrom,
393 const std::string& unitsTo)
394{
395 // we don't want to resize vector if no data to read
396 if (attrName.empty() || !holder.hasAttribute(attrName))
397 return false;
398
399 h5gt::Attribute attr = holder.getAttribute(attrName);
400 auto dtype = attr.getDataType();
401 if (!dtype.isTypeEqual(h5gt::AtomicType<T>()))
402 return false;
403
404 v.resize(holder.getAttribute(attrName).getMemSpace().getElementCount());
405 return _readAttribute(
406 holder, attrName, v.data(), v.size(), unitsFrom, unitsTo);
407}
408
409template <typename Object, typename T,
410 typename std::enable_if<
411 (std::is_same<Object, h5gt::File>::value ||
412 std::is_same<Object, h5gt::Group>::value ||
413 std::is_same<Object, h5gt::DataSet>::value) &&
414 std::is_arithmetic<T>::value>::type*>
415inline bool readAttribute(
416 Object& holder,
417 const std::string& attrName,
418 T &v,
419 const std::string& unitsFrom,
420 const std::string& unitsTo)
421{
422 return _readAttribute(
423 holder, attrName, &v, 1, unitsFrom, unitsTo);
424}
425
426template <typename Object, typename T,
427 typename std::enable_if<
428 std::is_same<Object, h5gt::File>::value ||
429 std::is_same<Object, h5gt::Group>::value ||
430 std::is_same<Object, h5gt::DataSet>::value>::type*>
432 Object& holder,
433 const std::string& attrName,
434 T *v,
435 size_t nElem)
436{
437 if (attrName.empty() || !holder.hasAttribute(attrName))
438 return false;
439
440 if (nElem == 0)
441 return false;
442
443 h5gt::Attribute attr = holder.getAttribute(attrName);
444 auto dtype_enum = h5gt::create_datatype<
445 typename std::remove_pointer<
446 typename std::remove_cv<T>::type>::type>();
447 auto dtype = attr.getDataType();
448 if (!dtype.isTypeEqual(dtype_enum) ||
449 attr.getMemSpace().getElementCount() != nElem)
450 return false;
451
452 attr.read(v);
453 return true;
454}
455
456template<typename Object, typename T,
457 typename std::enable_if<
458 (std::is_same<Object, h5gt::File>::value ||
459 std::is_same<Object, h5gt::Group>::value ||
460 std::is_same<Object, h5gt::DataSet>::value) &&
461 std::is_enum<T>::value>::type*>
462inline T readEnumAttribute(Object& object, const std::string& attrName)
463{
464 T value = static_cast<T>(0);
465 _readEnumAttribute(object, attrName, &value, 1);
466 return value;
467}
468
469template<typename Object, typename T,
470 typename std::enable_if<
471 (std::is_same<Object, h5gt::File>::value ||
472 std::is_same<Object, h5gt::Group>::value ||
473 std::is_same<Object, h5gt::DataSet>::value) &&
474 std::is_enum<T>::value>::type*>
475inline std::vector<T> readEnumVecAttribute(Object& object, const std::string& attrName)
476{
477 // we don't want to resize vector if no data to read
478 if (attrName.empty() || !object.hasAttribute(attrName))
479 return false;
480
481 h5gt::Attribute attr = object.getAttribute(attrName);
482 auto dtype_enum = h5gt::create_datatype<
483 typename std::remove_pointer<
484 typename std::remove_cv<T>::type>::type>();
485 auto dtype = attr.getDataType();
486 if (!dtype.isTypeEqual(dtype_enum))
487 return false;
488
489 std::vector<T> v;
490 v.resize(object.getAttribute(attrName).getMemSpace().getElementCount());
492 object, attrName, v.data(), v.size());
493 return v;
494}
495
496template <typename Object, typename T,
497 typename std::enable_if<
498 std::is_same<Object, h5gt::File>::value ||
499 std::is_same<Object, h5gt::Group>::value||
500 std::is_same<Object, h5gt::DataSet>::value>::type*>
502 Object& holder,
503 const std::string& attrName,
504 T* v,
505 size_t nElem,
506 const std::string& unitsFrom,
507 const std::string& unitsTo)
508{
509 if (attrName.empty())
510 return false;
511
512 if (nElem == 0)
513 return false;
514
515 if (!holder.hasAttribute(attrName))
516 holder.template createAttribute<T>(
517 attrName, h5gt::DataSpace({nElem}));
518
519 h5gt::Attribute attr = holder.getAttribute(attrName);
520 auto dtype = attr.getDataType();
521 if (!dtype.isTypeEqual(h5gt::AtomicType<T>()) ||
522 attr.getMemSpace().getElementCount() != nElem){
523 try {
524 holder.deleteAttribute(attrName);
525 attr = holder.template createAttribute<T>(
526 attrName, h5gt::DataSpace({nElem}));
527 } catch (h5gt::Exception e) {
528 return false;
529 }
530 }
531
532 if (!unitsFrom.empty() && !unitsTo.empty()){
533 double coef = units::convert(
534 units::unit_from_string(unitsFrom),
535 units::unit_from_string(unitsTo));
536 for(size_t i = 0; i < nElem; i++)
537 v[i] *= coef;
538 }
539
540 attr.write(v);
541 return true;
542}
543
544template<typename Object,
545 typename std::enable_if<
546 std::is_same<Object, h5gt::File>::value ||
547 std::is_same<Object, h5gt::Group>::value ||
548 std::is_same<Object, h5gt::DataSet>::value>::type*>
550 Object& holder,
551 const std::string& attrName,
552 const std::string& str)
553{
554 if (attrName.empty())
555 return false;
556
557 if (!holder.hasAttribute(attrName))
558 holder.template createAttribute<std::string>(
559 attrName, h5gt::DataSpace::From(str));
560
561 h5gt::Attribute attr = holder.getAttribute(attrName);
562 auto dtype = attr.getDataType();
563 if (!dtype.isTypeEqual(h5gt::AtomicType<std::string>()) ||
564 attr.getMemSpace().getElementCount() != 1)
565 return false;
566
567 attr.write(str);
568 return true;
569}
570
571template<typename Object, typename D,
572 typename std::enable_if<
573 (std::is_same<Object, h5gt::File>::value ||
574 std::is_same<Object, h5gt::Group>::value ||
575 std::is_same<Object, h5gt::DataSet>::value) &&
576 std::is_arithmetic<typename D::Scalar>::value>::type*>
578 Object& holder,
579 const std::string& attrName,
580 Eigen::DenseBase<D>& v,
581 const std::string& unitsFrom,
582 const std::string& unitsTo)
583{
584 return _overwriteAttribute(
585 holder, attrName, v.derived().data(), v.size(), unitsFrom, unitsTo);
586}
587
588template <typename Object, typename T,
589 typename std::enable_if<
590 (std::is_same<Object, h5gt::File>::value ||
591 std::is_same<Object, h5gt::Group>::value ||
592 std::is_same<Object, h5gt::DataSet>::value) &&
593 std::is_arithmetic<T>::value>::type*>
595 Object& holder,
596 const std::string& attrName,
597 std::vector<T>& v,
598 const std::string& unitsFrom,
599 const std::string& unitsTo)
600{
601 return _overwriteAttribute(
602 holder, attrName, v.data(), v.size(), unitsFrom, unitsTo);
603}
604
605template <typename Object, typename T,
606 typename std::enable_if<
607 (std::is_same<Object, h5gt::File>::value ||
608 std::is_same<Object, h5gt::Group>::value ||
609 std::is_same<Object, h5gt::DataSet>::value) &&
610 std::is_arithmetic<T>::value>::type*>
612 Object& holder,
613 const std::string& attrName,
614 T& v,
615 const std::string& unitsFrom,
616 const std::string& unitsTo)
617{
618 return _overwriteAttribute(
619 holder, attrName, &v, 1, unitsFrom, unitsTo);
620}
621
622template <typename Object, typename T,
623 typename std::enable_if<
624 std::is_same<Object, h5gt::File>::value ||
625 std::is_same<Object, h5gt::Group>::value||
626 std::is_same<Object, h5gt::DataSet>::value>::type*>
628 Object& holder,
629 const std::string& attrName,
630 T* v,
631 size_t nElem)
632{
633 if (attrName.empty())
634 return false;
635
636 if (nElem == 0)
637 return false;
638
639 auto dtype = h5gt::create_datatype<
640 typename std::remove_pointer<
641 typename std::remove_cv<T>::type>::type>();
642 if (!holder.hasAttribute(attrName))
643 holder.createAttribute(
644 attrName, h5gt::DataSpace({nElem}), dtype);
645
646 h5gt::Attribute attr = holder.getAttribute(attrName);
647 if (!dtype.isTypeEqual(dtype) ||
648 attr.getMemSpace().getElementCount() != nElem){
649 try {
650 holder.deleteAttribute(attrName);
651 attr = holder.createAttribute(
652 attrName, h5gt::DataSpace({nElem}), dtype);
653 } catch (h5gt::Exception e) {
654 return false;
655 }
656 }
657
658 attr.write(v);
659 return true;
660}
661
662template <typename Object, typename T,
663 typename std::enable_if<
664 (std::is_same<Object, h5gt::File>::value ||
665 std::is_same<Object, h5gt::Group>::value ||
666 std::is_same<Object, h5gt::DataSet>::value) &&
667 std::is_enum<T>::value>::type*>
669 Object& holder,
670 const std::string& attrName,
671 T& v)
672{
674 holder, attrName, &v, 1);
675}
676
677template <typename Object, typename T,
678 typename std::enable_if<
679 (std::is_same<Object, h5gt::File>::value ||
680 std::is_same<Object, h5gt::Group>::value ||
681 std::is_same<Object, h5gt::DataSet>::value) &&
682 std::is_enum<T>::value>::type*>
684 Object& holder,
685 const std::string& attrName,
686 std::vector<T>& v)
687{
689 holder, attrName, v.data(), v.size());
690}
691
692template<typename Object,
693 typename std::enable_if<
694 std::is_same<Object, h5gt::File>::value ||
695 std::is_same<Object, h5gt::Group>::value ||
696 std::is_same<Object, h5gt::DataSet>::value>::type*>
697inline unsigned readEnumAttribute(Object& object, const std::string& attrName){
698 /* as we often use magic_enum to convert enum to string
699 * we need to remove `h5geo::` from enum name given
700 * from magic_enum () as for example:
701 * magic_enum::enum_type_name<h5geo::SurveyType>() */
702// eraseSubStr(attrName, "h5geo::");
703
704 unsigned value = 0;
705 readAttribute(object, attrName, value);
706 return value;
707}
708
709template<typename Object,
710 typename std::enable_if<
711 std::is_same<Object, h5gt::File>::value ||
712 std::is_same<Object, h5gt::Group>::value ||
713 std::is_same<Object, h5gt::DataSet>::value>::type*>
714inline std::string readStringAttribute(Object& object, const std::string& attrName){
715 std::string str;
716 if (attrName.empty() || !object.hasAttribute(attrName))
717 return str;
718
719 h5gt::Attribute attr = object.getAttribute(attrName);
720 auto dtype = attr.getDataType();
721 if (!dtype.isTypeEqual(h5gt::AtomicType<std::string>()) ||
722 attr.getMemSpace().getElementCount() != 1)
723 return str;
724
725 attr.read(str);
726 return str;
727}
728
729template<typename Object,
730 typename std::enable_if<
731 std::is_same<Object, h5gt::File>::value ||
732 std::is_same<Object, h5gt::Group>::value ||
733 std::is_same<Object, h5gt::DataSet>::value>::type*>
735 Object& object, const std::string& attrName,
736 const std::string& unitsFrom,
737 const std::string& unitsTo){
738 float value = std::nan("nan");
739 readAttribute(object, attrName, value, unitsFrom, unitsTo);
740 return value;
741}
742
743template<typename Object,
744 typename std::enable_if<
745 std::is_same<Object, h5gt::File>::value ||
746 std::is_same<Object, h5gt::Group>::value ||
747 std::is_same<Object, h5gt::DataSet>::value>::type*>
749 Object& object, const std::string& attrName,
750 const std::string& unitsFrom,
751 const std::string& unitsTo)
752{
753 double value = std::nan("nan");
754 readAttribute(object, attrName, value, unitsFrom, unitsTo);
755 return value;
756}
757
758template<typename Object,
759 typename std::enable_if<
760 std::is_same<Object, h5gt::File>::value ||
761 std::is_same<Object, h5gt::Group>::value ||
762 std::is_same<Object, h5gt::DataSet>::value>::type*>
763inline std::vector<float> readFloatVecAttribute(
764 Object& object, const std::string& attrName,
765 const std::string& unitsFrom,
766 const std::string& unitsTo){
767 std::vector<float> value;
768 readAttribute(object, attrName, value, unitsFrom, unitsTo);
769 return value;
770}
771
772template<typename Object,
773 typename std::enable_if<
774 std::is_same<Object, h5gt::File>::value ||
775 std::is_same<Object, h5gt::Group>::value ||
776 std::is_same<Object, h5gt::DataSet>::value>::type*>
777inline std::vector<double> readDoubleVecAttribute(
778 Object& object, const std::string& attrName,
779 const std::string& unitsFrom,
780 const std::string& unitsTo){
781 std::vector<double> value;
782 readAttribute(object, attrName, value, unitsFrom, unitsTo);
783 return value;
784}
785
786template<typename Object,
787 typename std::enable_if<
788 std::is_same<Object, h5gt::File>::value ||
789 std::is_same<Object, h5gt::Group>::value ||
790 std::is_same<Object, h5gt::DataSet>::value>::type*>
791inline Eigen::VectorXf readFloatEigenVecAttribute(
792 Object& object, const std::string& attrName,
793 const std::string& unitsFrom,
794 const std::string& unitsTo){
795 Eigen::VectorXf value;
796 readAttribute(object, attrName, value, unitsFrom, unitsTo);
797 return value;
798}
799
800template<typename Object,
801 typename std::enable_if<
802 std::is_same<Object, h5gt::File>::value ||
803 std::is_same<Object, h5gt::Group>::value ||
804 std::is_same<Object, h5gt::DataSet>::value>::type*>
805inline Eigen::VectorXd readDoubleEigenVecAttribute(
806 Object& object, const std::string& attrName,
807 const std::string& unitsFrom,
808 const std::string& unitsTo){
809 Eigen::VectorXd value;
810 readAttribute(object, attrName, value, unitsFrom, unitsTo);
811 return value;
812}
813
814template<typename D>
816 h5gt::DataSet& dataset,
817 const std::string& attrName,
818 const Eigen::DenseBase<D>& v,
819 bool resize)
820{
821 if (v.size() == 0)
822 return false;
823
824 ptrdiff_t ind = h5geo::getIndexFromAttribute(
825 dataset, attrName);
826
827 if (ind < 0)
828 return false;
829
830 std::vector dims = dataset.getDimensions();
831
832 if (resize == false &&
833 dims[1] != v.size())
834 return false;
835
836 if (resize == true &&
837 dims[1] != v.size())
838 dataset.resize({dims[0], size_t(v.size())});
839
840 try {
841 dataset.select({size_t(ind), 0}, {1, size_t(v.size())}).
842 write_raw(v.derived().data());
843 } catch (h5gt::Exception e) {
844 return false;
845 }
846
847 return true;
848}
849
850template<typename T>
851inline Eigen::VectorX<T> getDataFromIndexedDataset(
852 h5gt::DataSet& dataset,
853 const std::string& attrName)
854{
855 ptrdiff_t ind = h5geo::getIndexFromAttribute(
856 dataset, attrName);
857
858 if (ind < 0)
859 return Eigen::VectorXd();
860
861 std::vector dims = dataset.getDimensions();
862 Eigen::VectorX<T> v(dims[1]);
863
864 try {
865 dataset.select({size_t(ind), 0}, {1, dims[1]}).
866 read(v.derived().data());
867 } catch (h5gt::Exception e) {
868 return Eigen::VectorX<T>();
869 }
870
871 return v;
872}
873
874// UTIL
875
876template<typename Object,
877 typename std::enable_if<
878 std::is_same<Object, h5gt::File>::value ||
879 std::is_same<Object, h5gt::Group>::value ||
880 std::is_same<Object, h5gt::DataSet>::value>::type*>
881inline bool deleteAllAttributes(Object& object){
882 try {
883 std::vector<std::string> attrNameList =
884 object.listAttributeNames();
885 for (const auto& name : attrNameList)
886 object.deleteAttribute(name);
887 } catch (h5gt::Exception e) {
888 return false;
889 }
890 return true;
891}
892
893template<typename Object,
894 typename std::enable_if<
895 std::is_same<Object, h5gt::File>::value ||
896 std::is_same<Object, h5gt::Group>::value>::type*>
897inline bool unlinkContent(Object& object){
898 try {
899 std::vector<std::string> objNames =
900 object.listObjectNames();
901 for (const auto& name : objNames)
902 object.unlink(name);
903 } catch (h5gt::Exception e) {
904 return false;
905 }
906 return true;
907}
908
909template<typename T>
910inline Eigen::VectorX<ptrdiff_t> find_index(
911 Eigen::DenseBase<T> const & M){
912 Eigen::VectorX<ptrdiff_t> ind(M.size());
913 ptrdiff_t ii = 0;
914 for (ptrdiff_t i = 0; i < M.size(); i++){
915 if (M(i) != 0){
916 ind(ii) = i;
917 ii++;
918 }
919 }
920 ind.conservativeResize(ii);
921
922 return ind;
923}
924
925template<typename D, typename T,
926 typename std::enable_if<
927 std::is_arithmetic<T>::value>::type*>
928inline h5gt::ElementSet rowCols2ElementSet(
929 const T& row,
930 const Eigen::DenseBase<D>& cols)
931{
932 ptrdiff_t I = cols.size();
933 std::vector<size_t> v(2*I, row);
934
935 for (ptrdiff_t i = 0; i < I; i++)
936 v[2*i+1] = cols(i);
937
938 return h5gt::ElementSet(v);
939}
940
941template<typename D, typename T,
942 typename std::enable_if<
943 std::is_arithmetic<T>::value>::type*>
944inline h5gt::ElementSet rowsCol2ElementSet(
945 const Eigen::DenseBase<D>& rows,
946 const T& col)
947{
948 ptrdiff_t I = rows.size();
949 std::vector<size_t> v(2*I, col);
950
951 for (ptrdiff_t i = 0; i < I; i++)
952 v[2*i] = rows(i);
953
954 return h5gt::ElementSet(v);
955}
956
957template<typename D>
958inline h5gt::ElementSet rowsCols2ElementSet(
959 const Eigen::DenseBase<D>& rows,
960 const Eigen::DenseBase<D>& cols)
961{
962 ptrdiff_t I = rows.size();
963 ptrdiff_t J = cols.size();
964
965 std::vector<size_t> v(2*I*J);
966
967 for (ptrdiff_t i = 0; i < I; i++){
968 for (ptrdiff_t j = 0; j < J; j++){
969 v[2*j + 2*i*J] = rows(i);
970 v[2*j+1 + 2*i*J] = cols(j);
971 }
972 }
973
974 return h5gt::ElementSet(v);
975}
976
977template<typename T,
978 typename std::enable_if<
979 std::is_arithmetic<T>::value>::type*>
980inline h5gt::ElementSet rowCols2ElementSet(
981 const T& row,
982 const std::vector<T>& cols)
983{
984 size_t I = cols.size();
985 std::vector<size_t> v(2*I, row);
986
987 for (size_t i = 0; i < I; i++)
988 v[2*i+1] = cols[i];
989
990 return h5gt::ElementSet(v);
991}
992
993template<typename T,
994 typename std::enable_if<
995 std::is_arithmetic<T>::value>::type*>
996inline h5gt::ElementSet rowsCol2ElementSet(
997 const std::vector<T>& rows,
998 const T& col)
999{
1000 size_t I = rows.size();
1001 std::vector<size_t> v(2*I, col);
1002
1003 for (size_t i = 0; i < I; i++)
1004 v[2*i] = rows[i];
1005
1006 return h5gt::ElementSet(v);
1007}
1008
1009template<typename T,
1010 typename std::enable_if<
1011 std::is_arithmetic<T>::value>::type*>
1012inline h5gt::ElementSet rowsCols2ElementSet(
1013 const std::vector<T>& rows,
1014 const std::vector<T>& cols)
1015{
1016 size_t I = rows.size();
1017 size_t J = cols.size();
1018
1019 std::vector<size_t> v(2*I*J);
1020
1021 for (size_t i = 0; i < I; i++){
1022 for (size_t j = 0; j < J; j++){
1023 v[2*j + 2*i*J] = rows[i];
1024 v[2*j+1 + 2*i*J] = cols[j];
1025 }
1026 }
1027
1028 return h5gt::ElementSet(v);
1029}
1030
1031} // namespace h5geo
1032
1033#endif // H5COREIMPL_H
Basic namespace.
Definition h5base.h:29
std::vector< float > readFloatVecAttribute(Object &object, const std::string &attrName, const std::string &unitsFrom="", const std::string &unitsTo="")
Read data from Attribute.
Definition h5coreimpl.h:763
Eigen::VectorXd readDoubleEigenVecAttribute(Object &object, const std::string &attrName, const std::string &unitsFrom="", const std::string &unitsTo="")
Read data from Attribute.
Definition h5coreimpl.h:805
std::vector< double > readDoubleVecAttribute(Object &object, const std::string &attrName, const std::string &unitsFrom="", const std::string &unitsTo="")
Read data from Attribute.
Definition h5coreimpl.h:777
bool unlinkContent(Object &object)
unlinkContent Unlink everything in group
Definition h5coreimpl.h:897
bool _overwriteDataset(Object &node, const std::string &datasetPath, T *M, size_t nH5Rows, size_t nH5Cols, const std::string &unitsFrom="", const std::string &unitsTo="")
Create or overwrite DataSet.
Definition h5coreimpl.h:128
bool _readEnumAttribute(Object &holder, const std::string &attrName, T *v, size_t nElem)
Read enum data from Attribute.
Definition h5coreimpl.h:431
h5gt::ElementSet rowsCols2ElementSet(const Eigen::DenseBase< D > &rows, const Eigen::DenseBase< D > &cols)
rowsCols2ElementSet select rectilinear block of elements, i.e. uses double loop to select every possi...
Definition h5coreimpl.h:958
Eigen::VectorX< T > getDataFromIndexedDataset(h5gt::DataSet &dataset, const std::string &attrName)
Get data from indexed DataSet.
Definition h5coreimpl.h:851
bool _readDataset(Object &node, const std::string &datasetPath, T *M, size_t nElem, const std::string &unitsFrom="", const std::string &unitsTo="")
Read data from DataSet to buffer.
Definition h5coreimpl.h:222
bool readDataset(Object &node, const std::string &datasetPath, Eigen::DenseBase< D > &M, const std::string &unitsFrom="", const std::string &unitsTo="")
Read data from DataSet.
Definition h5coreimpl.h:262
bool _overwriteAttribute(Object &holder, const std::string &attrName, T *v, size_t nElem, const std::string &unitsFrom="", const std::string &unitsTo="")
Create or overwrite Attribute.
Definition h5coreimpl.h:501
bool _readAttribute(Object &holder, const std::string &attrName, T *v, size_t nElem, const std::string &unitsFrom="", const std::string &unitsTo="")
Read data from Attribute.
Definition h5coreimpl.h:322
bool writeDataToIndexedDataset(h5gt::DataSet &dataset, const std::string &attrName, const Eigen::DenseBase< D > &v, bool resize)
writeDataToIndexedDataset Try to write vector to dataset with attribute where attribute is a single v...
Definition h5coreimpl.h:815
bool overwriteDataset(Object &node, const std::string &datasetPath, Eigen::DenseBase< D > &M, const std::string &unitsFrom="", const std::string &unitsTo="")
Create or overwrite DataSet.
Definition h5coreimpl.h:175
bool overwriteResizableDataset(Object &node, const std::string &datasetPath, Eigen::DenseBase< D > &M, const std::string &unitsFrom="", const std::string &unitsTo="")
Resize and overwrite DataSet or create it if not exists.
Definition h5coreimpl.h:81
double readDoubleAttribute(Object &object, const std::string &attrName, const std::string &unitsFrom="", const std::string &unitsTo="")
Read data from Attribute.
Definition h5coreimpl.h:748
Eigen::MatrixXf readFloatEigenMtxDataset(Object &node, const std::string &datasetPath, const std::string &unitsFrom="", const std::string &unitsTo="")
Read data from DataSet.
Definition h5coreimpl.h:289
H5GEO_EXPORT ptrdiff_t getIndexFromAttribute(h5gt::DataSet &dataset, const std::string &attrName)
getIndexFromAttribute Get row/col from Datasets with attributes where attribute reflects the row/col ...
Definition h5core.cpp:701
Eigen::VectorXf readFloatEigenVecAttribute(Object &object, const std::string &attrName, const std::string &unitsFrom="", const std::string &unitsTo="")
Read data from Attribute.
Definition h5coreimpl.h:791
float readFloatAttribute(Object &object, const std::string &attrName, const std::string &unitsFrom="", const std::string &unitsTo="")
Read data from Attribute.
Definition h5coreimpl.h:734
bool readAttribute(Object &holder, const std::string &attrName, Eigen::DenseBase< D > &v, const std::string &unitsFrom="", const std::string &unitsTo="")
Read data from Attribute.
Definition h5coreimpl.h:361
bool _overwriteResizableDataset(Object &node, const std::string &datasetPath, T *M, size_t nH5Rows, size_t nH5Cols, const std::string &unitsFrom="", const std::string &unitsTo="")
Resize and overwrite DataSet or create it if not exists.
Definition h5coreimpl.h:33
std::string readStringAttribute(Object &object, const std::string &attrName)
Read enum data from Attribute.
Definition h5coreimpl.h:714
bool overwriteAttribute(Object &holder, const std::string &attrName, const std::string &str)
Create or overwrite Attribute.
Definition h5coreimpl.h:549
std::vector< T > readEnumVecAttribute(Object &object, const std::string &attrName)
Read data from Attribute.
Definition h5coreimpl.h:475
Eigen::MatrixXd readDoubleEigenMtxDataset(Object &node, const std::string &datasetPath, const std::string &unitsFrom="", const std::string &unitsTo="")
Read data from DataSet.
Definition h5coreimpl.h:305
Eigen::VectorX< ptrdiff_t > find_index(Eigen::DenseBase< T > const &M)
find_index find all non-zero elements's indexes. Possible usage: Eigen::VectorX<ptrdiff_t> ind = find...
Definition h5coreimpl.h:910
bool _overwriteEnumAttribute(Object &holder, const std::string &attrName, T *v, size_t nElem)
Create or overwrite registered enum Attribute.
Definition h5coreimpl.h:627
bool overwriteEnumAttribute(Object &holder, const std::string &attrName, T &v)
Create or overwrite registered enum Attribute.
Definition h5coreimpl.h:668
T readEnumAttribute(Object &object, const std::string &attrName)
Read data from Attribute.
Definition h5coreimpl.h:462