LArSoft  v06_85_00
Liquid Argon Software toolkit - http://larsoft.org/
TableMemberRegistry.h
Go to the documentation of this file.
1 #ifndef fhiclcpp_types_detail_TableMemberRegistry_h
2 #define fhiclcpp_types_detail_TableMemberRegistry_h
3 
4 /*
5 
6  'TableMemberRegistry' exists solely because C++ does not have the
7  reflection facilities required to return the members of a struct or
8  class, which is needed to walk through the members of a table. For
9  example, consider the following struct and associated Table<S>
10  object:
11 
12  struct S {
13  Atom<int> n { Name("num") };
14  Sequence<int> l { Name("list") };
15  };
16  Table<S> t { Name("t") };
17 
18  C++ does not have the ability to return the list of data members for
19  the struct 'S'. The registration system below, however, does do
20  this by taking the Name values above ("num" and "list"), and emplacing
21  them into a container corresponding to the table members associated with 't'.
22 
23  The way this registry is used is via private inheritance of a
24  'RegisterIfTableMember' auxiliary class. Each fhiclcpp parameter
25  type (Atom, Sequence, etc.), inherits from the auxiliary class.
26 
27  If the C++ reflection facilities improve to the level that a
28  struct's or class's members can be returned (either at compile-time,
29  or run-time), this registry should be removed.
30 
31 */
32 
33 #include "cetlib/exempt_ptr.h"
36 
37 #include <stack>
38 #include <vector>
39 
40 namespace fhicl {
41 
42  class ParameterSet;
43 
44  namespace detail {
45 
46  // All-private class that only
47  // fhicl::detail::RegisterIfTableMember, fhicl::Table, and
48  // fhicl::OptionalTable can access via friendship.
49 
51  public:
52  // Disable copy/move operations
57 
58  private:
59  TableMemberRegistry() = default;
60 
61  using base_ptr = cet::exempt_ptr<ParameterBase>;
62  using table_members_t = std::vector<base_ptr>;
63  std::stack<table_members_t> tables_;
64 
65  static TableMemberRegistry&
67  {
68  static TableMemberRegistry registry;
69  return registry;
70  }
71 
72  // Retrieval facilities for fhicl::(Optional)Table
73 
74  template <typename T, typename KeysToIgnore>
75  friend class fhicl::Table;
76  template <typename T>
77  friend class fhicl::OptionalTable;
78 
79  std::vector<base_ptr>
81  {
82  std::vector<base_ptr> result;
83  std::swap(tables_.top(), result);
84  tables_.pop();
85  return result;
86  }
87 
88  // Registration facilities
89 
90  friend class RegisterIfTableMember;
91  void
93  {
94  tables_.top().emplace_back(pb);
95  }
96 
97  void
99  {
100  tables_.emplace();
101  }
102  };
103 
104  //========================================================
106  public:
108  {
109  if (is_table_member(pb->key())) {
111  }
112  if (is_table(pb->parameter_type())) {
114  }
115  }
116  };
117  }
118 }
119 
120 #endif /* fhiclcpp_types_detail_TableMemberRegistry_h */
121 
122 // Local variables:
123 // mode: c++
124 // End:
TableMemberRegistry & operator=(TableMemberRegistry const &)=delete
std::stack< table_members_t > tables_
bool is_table(boost::any const &val)
Definition: coding.h:56
std::vector< base_ptr > table_members_t
void emplace_table_member(ParameterBase *pb)
static TableMemberRegistry & instance()
parameter set interface
par_type parameter_type() const
Definition: ParameterBase.h:74
std::vector< base_ptr > release_members()
cet::exempt_ptr< ParameterBase > base_ptr
bool is_table_member(std::string const &key)
std::string key() const
Definition: ParameterBase.h:44