8 #ifndef IMPKERNEL_KEY_H
9 #define IMPKERNEL_KEY_H
12 #include "internal/key_helpers.h"
19 #include <cereal/access.hpp>
22 IMPKERNEL_BEGIN_NAMESPACE
44 template <
unsigned int ID>
50 static internal::KeyData& get_key_data() {
51 #ifndef IMPKERNEL_INTERNAL_OLD_COMPILER
52 static internal::KeyData static_key_data_(ID);
53 return static_key_data_;
55 return IMP::internal::get_key_data(ID);
62 friend class cereal::access;
64 template<
class Archive>
void serialize(Archive &ar) {
68 if (std::is_base_of<cereal::detail::OutputArchiveBase, Archive>::value) {
80 str_ = find_or_add_index(name);
85 static const internal::KeyData::Map& get_map() {
86 return get_key_data().get_map();
88 static const internal::KeyData::RMap& get_rmap() {
89 IMP::internal::KeyData
const& kd=get_key_data();
90 IMP::internal::KeyData::RMap
const& ret=kd.get_rmap();
95 static unsigned int find_or_add_index(std::string
const& sc) {
99 auto it = get_map().find(sc);
100 if (it == get_map().end()) {
101 val = get_key_data().add_key(sc);
110 static unsigned int find_index(std::string
const& sc) {
114 IMP_USAGE_CHECK( get_key_exists(sc),
"Key<" << ID <<
">::find_index():"
115 <<
" You must explicitly create the type first: "
117 val = get_map().find(sc)->second;
123 bool is_default()
const;
126 #if !defined(IMP_DOXYGEN) && !defined(SWIG)
127 static unsigned int get_ID() {
return ID; }
129 static const std::string get_string(
int i) {
132 if (static_cast<unsigned int>(i) < get_rmap().size()) {
138 << i <<
" with a table of size " << get_rmap().size());
160 explicit Key(std::string
const& c,
bool is_implicit_add_permitted=
true)
161 : str_(is_implicit_add_permitted ? find_or_add_index(c) : find_index(c))
164 #if !defined(IMP_DOXYGEN)
167 explicit Key(
unsigned int i) : str_(i) {
173 static unsigned int add_key(
const std::string &sc) {
178 val = get_key_data().add_key(sc);
185 static
Key get_existing_key(std::
string const& sc) {
188 auto it = get_map().find(sc);
189 if (it != get_map().end()) {
190 ret =
Key(static_cast<unsigned int>(it->second));
200 val = get_map().find(sc) != get_map().end();
206 if (is_default())
return std::string(
"nullptr");
208 val = get_string(str_);
225 std::string new_name) {
227 "The name is already taken with an existing key or alias");
228 get_key_data().add_alias(new_name, old_key.get_index());
229 return Key<ID>(new_name.c_str());
232 static unsigned int get_number_of_keys() {
233 return get_rmap().size();
239 "Cannot get index on defaultly constructed Key");
245 static void show_all(std::ostream& out);
251 static Vector<std::string> get_all_strings();
271 Key operator+(
int o)
const {
282 template <
unsigned int ID>
283 inline std::ostream& operator<<(std::ostream& out, Key<ID> k) {
288 template <
unsigned int ID>
289 inline bool Key<ID>::is_default()
const {
293 template <
unsigned int ID>
294 inline void Key<ID>::show_all(std::ostream& out) {
296 get_key_data().
show(out);
299 template <
unsigned int ID>
300 Vector<std::
string> Key<ID>::get_all_strings() {
301 Vector<std::string> str;
303 for (internal::KeyData::Map::const_iterator it = get_map().begin();
304 it != get_map().end(); ++it) {
305 str.push_back(it->first);
311 IMPKERNEL_END_NAMESPACE
#define IMP_SHOWABLE_INLINE(Name, how_to_show)
Declare the methods needed by an object that can be printed.
Helper macros for implementing comparisons of IMP objects.
#define IMP_FAILURE(message)
A runtime failure for IMP.
#define IMP_HASHABLE_INLINE(name, hashret)
Key()
make a default key in a well-defined null state
#define IMP_LOG_PROGRESS(expr)
const std::string get_string() const
Turn a key into a pretty string.
#define IMP_INTERNAL_CHECK(expr, message)
An assertion to check for internal errors in IMP. An IMP::ErrorException will be thrown.
Base class for a simple primitive-like type.
static unsigned int get_number_unique()
Get the total number of keys of this type.
static bool get_key_exists(const std::string &sc)
Return true if there already is a key with that string.
Ints get_index(const ParticlesTemp &particles, const Subset &subset, const Subsets &excluded)
Helper macros for implementing hashable classes.
Logging and error reporting support.
Various general useful functions for IMP.
std::ostream & show(Hierarchy h, std::ostream &out=std::cout)
Print the hierarchy using a given decorator to display each node.
Helper macros for throwing and handling exceptions.
Base class for a simple primitive-like type.
#define IMP_USAGE_CHECK(expr, message)
A runtime test for incorrect usage of a class or method.
static Key< ID > add_alias(Key< ID > old_key, std::string new_name)
Make new_name an alias for old_key.
#define IMP_COMPARISONS_1(Name, field)
Implement comparison in a class using field as the variable to compare.
Key(std::string const &c, bool is_implicit_add_permitted=true)
Generate a key object from the given string.
#define IMP_OMP_PRAGMA(x)