IODA
Layout.h
Go to the documentation of this file.
1 #pragma once
2 /*
3  * (C) Copyright 2020-2021 UCAR
4  *
5  * This software is licensed under the terms of the Apache Licence Version 2.0
6  * which can be obtained at http://www.apache.org/licenses/LICENSE-2.0.
7  */
8 /*! \addtogroup ioda_cxx_layout
9  *
10  * @{
11  * \file Layout.h
12  * \brief Contains definitions for how data are arranged in ioda internally.
13  */
14 
15 #include <memory>
16 #include <string>
17 #include <typeindex>
18 #include <utility>
19 
20 #include "ioda/defs.h"
21 
22 namespace ioda {
23 class Group;
24 
25 namespace detail {
26 class Group_Base;
27 class Group_Backend;
28 class DataLayoutPolicy;
29 
30 /// \brief Policy used for setting locations for Variable access
31 /// \ingroup ioda_cxx_layout
32 /// \note Using std::enable_shared_from_this as part of the pybind11 interface.
33 /// We pass this to ObsGroup as a shared_ptr.
34 /// See https://pybind11.readthedocs.io/en/stable/advanced/smart_ptrs.html#std-shared-ptr
35 class IODA_DL DataLayoutPolicy : public std::enable_shared_from_this<DataLayoutPolicy> {
36 public:
37  virtual ~DataLayoutPolicy();
38  enum class Policies {
39  /// Do no manipulation of the Group / Variable layout.
40  None,
41  /// Transform "Variable@Group" into "Group/Variable". Ensure that
42  /// group names match a few predefined keys.
43  ObsGroup,
44  /// Uses an auxiliary YAML dictionary to convert ODB variable/group naming conventions to
45  /// IODA equivalents. Transform "Variable@Group" into "Group/Variable". Ensure that
46  /// the new group names match a few predefined keys.
47  ObsGroupODB
48  };
49  enum class MergeMethod {
50  /// Concatenate complementary variables entry-by-entry
51  Concat
52  };
53 
54  /// Factory generator.
55  static std::shared_ptr<const DataLayoutPolicy> generate(const std::string &polid = "");
56  /// Factory generator (ODB-specific)
57  /// \p mapPath path to a yaml file that defines how input file variables should be renamed
58  /// upon import to ioda.
59  static std::shared_ptr<const DataLayoutPolicy> generate(const std::string &polid,
60  const std::string &mapPath);
61  /// Factory generator.
62  static std::shared_ptr<const DataLayoutPolicy> generate(Policies pol = Policies::None);
63  /// Factory generator (ODB-specific)
64  /// \p mapPath path to a yaml file that defines how input file variables should be renamed
65  /// upon import to ioda.
66  static std::shared_ptr<const DataLayoutPolicy> generate(Policies pol,
67  const std::string &mapPath);
68  /// \internal pybind11 overload casts do not work on some compilers.
69  static inline std::shared_ptr<const DataLayoutPolicy> _py_generate1(const std::string &polid) {
70  return generate(polid);
71  }
72  /// \internal pybind11 overload casts do not work on some compilers.
73  static inline std::shared_ptr<const DataLayoutPolicy> _py_generate2(Policies pol) {
74  return generate(pol);
75  }
76 
77  /// Create default groups and write default attributes upon object
78  /// creation / initialization.
79  virtual void initializeStructure(Group_Base &) const;
80  /// \brief Map a user-specified Variable path to the correct location.
81  /// \details This allows us to keep the frontend paths consistent, and we
82  /// can instead do a path transformation to hide implementation details
83  /// from end users.
84  ///
85  /// The default policy is to pass paths expressed with forward slashes ("MetaData/Longitude")
86  /// unchanged. If we pass paths using '@' notation, then reverse the path component
87  /// (i.e. "TB@ObsValue" becomes "ObsValue/TB").
88  /// \note We can apply these policies in both the frontend and inside of the engines.
89  /// \param inStr is the user-provided string. Ex: "TB@ObsValue" or "MetaData/Latitude",
90  /// or even a fundamental dimension ("ChannelNumber").
91  /// \returns A canonical path, always of the form "Group/Variable". In case of a dimension
92  /// scale, then there is no group name, but for every other Variable, there is a Group name.
93  virtual std::string doMap(const std::string &) const;
94 
95  /// Check if the named variable will be a part of a derived variable
96  virtual bool isComplementary(const std::string &) const;
97 
98  /// Check if the named variable is in the Variables section of the ODB mapping file.
99  virtual bool isMapped(const std::string &) const;
100 
101  /// Returns the position of the input variable in the derived variable.
102  /// \throws If the input is not part of a derived variable.
103  virtual size_t getComplementaryPosition(const std::string &) const;
104 
105  /// Returns the derived variable name to be used in ioda.
106  /// \throws If the input is not part of a derived variable.
107  virtual std::string getOutputNameFromComponent(const std::string &) const;
108 
109  /// Returns the data type of the derived variable.
110  /// \throws If the input is not part of a derived variable.
111  virtual std::type_index getOutputVariableDataType(const std::string &) const;
112 
113  /// Returns the merge method for derived variables.
114  /// \throws If the input is not part of a derived variable.
115  virtual MergeMethod getMergeMethod(const std::string &) const;
116 
117  /// Returns the count of input variables needed.
118  /// \throws If the input is not part of a derived variable.
119  virtual size_t getInputsNeeded(const std::string &) const;
120 
121  /// Returns the variable's unit if it has been specified.
122  /// \returns A pair of (found, unit) indicating if a unit was found and what it is.
123  /// \throws If the input is not listed in Variables section of mapping file.
124  virtual std::pair<bool, std::string> getUnit(const std::string &) const;
125 
126  /// A descriptive name for the policy.
127  virtual std::string name() const;
128 
130 };
131 } // namespace detail
132 } // namespace ioda
133 
134 /// @}
An ObsGroup is a specialization of a ioda::Group. It provides convenience functions and guarantees th...
Definition: ObsGroup.h:32
Policy used for setting locations for Variable access.
Definition: Layout.h:35
static std::shared_ptr< const DataLayoutPolicy > _py_generate1(const std::string &polid)
Definition: Layout.h:69
static std::shared_ptr< const DataLayoutPolicy > _py_generate2(Policies pol)
Definition: Layout.h:73
Hidden base class to prevent constructor confusion.
Definition: Group.h:42
Common preprocessor definitions used throughout IODA.
#define IODA_DL
A preprocessor tag that indicates that a symbol is to be exported/imported.
Definition: defs.h:110