Empirical
ConfigManager.h
Go to the documentation of this file.
1 // This file is part of Empirical, https://github.com/devosoft/Empirical
2 // Copyright (C) Michigan State University, 2016.
3 // Released under the MIT Software license; see doc/LICENSE
4 //
5 //
6 // The ConfigManager templated class handles the building and configuration of new objects
7 // of the target type.
8 //
9 // The manager is created with two keywords; one for the type of the managed class, and the
10 // other for the keyword to trigger commands for it.
11 //
12 // For example, if we're configuring an instruction set, the type might be 'inst_set' and the
13 // keyword might be 'inst'. Then the configuration file can have lines like:
14 //
15 // new inst_lib 4stack
16 // inst nopA
17 // inst inc
18 // inst divide cycle_cost=10
19 // ...
20 
21 
22 #ifndef EMP_CONFIG_MANAGER_H
23 #define EMP_CONFIG_MANAGER_H
24 
25 #include <functional>
26 #include <iostream>
27 #include <map>
28 #include <string>
29 #include <sstream>
30 
31 namespace emp {
32 
34  protected:
35  const std::string type_keyword;
36  const std::string command_keyword;
37 
38  public:
39  ConfigManager_Base(const std::string & _type, const std::string & _command)
40  : type_keyword(_type), command_keyword(_command) { ; }
41  virtual ~ConfigManager_Base() { ; }
42 
43  const std::string & GetTypeKeyword() const { return type_keyword; }
44  const std::string & GetCommandKeyword() const { return command_keyword; }
45 
46  virtual void NewObject(const std::string & obj_name) = 0;
47  virtual void UseObject(const std::string & obj_name) = 0;
48  virtual bool CommandCallback(const std::string & command) = 0;
49  };
50 
51  template <class MANAGED_TYPE> class ConfigManager : public ConfigManager_Base {
52  private:
53  std::map<std::string, MANAGED_TYPE *> name_map;
54  MANAGED_TYPE * cur_obj;
55  std::function<bool(MANAGED_TYPE &, std::string)> callback_fun;
56 
57  public:
58  ConfigManager(const std::string & _type, const std::string & _command,
59  std::function<bool(MANAGED_TYPE &, std::string)> _fun)
60  : ConfigManager_Base(_type, _command)
61  , cur_obj(nullptr)
62  , callback_fun(_fun)
63  {
64  }
66 
67  bool HasObject(const std::string & obj_name) {
68  return (name_map.find(obj_name) != name_map.end());
69  }
70 
71  void NewObject(const std::string & obj_name) {
72  if (HasObject(obj_name) == true) {
73  std::stringstream ss;
74  ss << "Building new object of type '" << type_keyword << "' named '"
75  << obj_name << "' when one already exists. Replacing." << std::endl;
76  NotifyError(ss.str());
77  delete name_map[obj_name];
78  }
79  cur_obj = new MANAGED_TYPE;
80  name_map[obj_name] = cur_obj;
81  }
82 
83  void UseObject(const std::string & obj_name) {
84  if (HasObject(obj_name) == false) {
85  std::stringstream ss;
86  ss << "Trying to use object of type '" << type_keyword << "' named '"
87  << obj_name << "', but does not exist. Ignoring." << std::endl;
88  NotifyError(ss.str());
89  return;
90  }
91  cur_obj = name_map[obj_name];
92  }
93 
94  bool CommandCallback(const std::string & command) {
95  if (cur_obj == nullptr) {
96  std::stringstream ss;
97  ss << "Must build new '" << type_keyword << "' object before using command '"
98  << command_keyword << "'. Ignoring." << std::endl;
99  NotifyError(ss.str());
100  return false;
101  }
102 
103  return callback_fun(*cur_obj, command);
104  }
105  };
106 
107 }
108 
109 #endif
ConfigManager(const std::string &_type, const std::string &_command, std::function< bool(MANAGED_TYPE &, std::string)> _fun)
Definition: ConfigManager.h:58
void NewObject(const std::string &obj_name)
Definition: ConfigManager.h:71
const std::string type_keyword
Definition: ConfigManager.h:35
virtual bool CommandCallback(const std::string &command)=0
void NotifyError(Ts &&...msg)
End user has done something resulting in an non-recoverable problem.
Definition: errors.h:145
const std::string command_keyword
Definition: ConfigManager.h:36
ConfigManager_Base(const std::string &_type, const std::string &_command)
Definition: ConfigManager.h:39
bool CommandCallback(const std::string &command)
Definition: ConfigManager.h:94
static const PrintStr endl("<br>")
Pre-define emp::endl to insert a "<br>" and thus acting like a newline.
Definition: ConfigManager.h:33
bool HasObject(const std::string &obj_name)
Definition: ConfigManager.h:67
If we are in emscripten, make sure to include the header.
Definition: array.h:37
virtual void UseObject(const std::string &obj_name)=0
~ConfigManager()
Definition: ConfigManager.h:65
const std::string & GetCommandKeyword() const
Definition: ConfigManager.h:44
virtual ~ConfigManager_Base()
Definition: ConfigManager.h:41
const std::string & GetTypeKeyword() const
Definition: ConfigManager.h:43
Definition: ConfigManager.h:51
virtual void NewObject(const std::string &obj_name)=0
void UseObject(const std::string &obj_name)
Definition: ConfigManager.h:83