OpenMD
3.2
Molecular Dynamics in the Open
Toggle main menu visibility
Loading...
Searching...
No Matches
GenericFactory.hpp
Go to the documentation of this file.
1
/*
2
* Copyright (c) 2004-present, The University of Notre Dame. All rights
3
* reserved.
4
*
5
* Redistribution and use in source and binary forms, with or without
6
* modification, are permitted provided that the following conditions are met:
7
*
8
* 1. Redistributions of source code must retain the above copyright notice,
9
* this list of conditions and the following disclaimer.
10
*
11
* 2. Redistributions in binary form must reproduce the above copyright notice,
12
* this list of conditions and the following disclaimer in the documentation
13
* and/or other materials provided with the distribution.
14
*
15
* 3. Neither the name of the copyright holder nor the names of its
16
* contributors may be used to endorse or promote products derived from
17
* this software without specific prior written permission.
18
*
19
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
20
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
23
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29
* POSSIBILITY OF SUCH DAMAGE.
30
*
31
* SUPPORT OPEN SCIENCE! If you use OpenMD or its source code in your
32
* research, please cite the following paper when you publish your work:
33
*
34
* [1] Drisko et al., J. Open Source Softw. 9, 7004 (2024).
35
*
36
* Good starting points for code and simulation methodology are:
37
*
38
* [2] Meineke, et al., J. Comp. Chem. 26, 252-271 (2005).
39
* [3] Fennell & Gezelter, J. Chem. Phys. 124, 234104 (2006).
40
* [4] Sun, Lin & Gezelter, J. Chem. Phys. 128, 234107 (2008).
41
* [5] Vardeman, Stocker & Gezelter, J. Chem. Theory Comput. 7, 834 (2011).
42
* [6] Kuang & Gezelter, Mol. Phys., 110, 691-701 (2012).
43
* [7] Lamichhane, Gezelter & Newman, J. Chem. Phys. 141, 134109 (2014).
44
* [8] Bhattarai, Newman & Gezelter, Phys. Rev. B 99, 094106 (2019).
45
* [9] Drisko & Gezelter, J. Chem. Theory Comput. 20, 4986-4997 (2024).
46
*/
47
48
/**
49
* @file GenericFactory.hpp
50
* @author Teng Lin
51
* @date 10/24/2004
52
* @version 1.0
53
*/
54
55
#ifndef UTIL_GENERICFACTORY_HPP
56
#define UTIL_GENERICFACTORY_HPP
57
58
#include <cassert>
59
#include <map>
60
#include <string>
61
#include <vector>
62
63
namespace
OpenMD
{
64
65
/**
66
* @class GenericFactory GenericFactory.hpp "utils/GenericFactory.hpp"
67
* @brief GenericFactory is a template based Object Factory
68
* Factory pattern is used to define an interface for creating an object.
69
*
70
* @param Object the base class of the hierarchy for which you provide the
71
object factory.
72
* @param IdentType the object that identifies the type of the concrete
73
object. Default type is std::string * @param Creator the callable entity
74
that creates objects. This type must support operator(),
75
* taking no parameters and returning a pointer to Object. Default type is
76
function pointer.
77
*
78
* Usage:
79
* @code
80
* //Shape class
81
* class Shape {
82
* ...
83
* };
84
*
85
* //instantiating a new object factory
86
* using ShapeFactory = GenericFactory<Shape>;
87
*
88
* //Line class
89
* class Line : public Shape{
90
* ...
91
* };
92
*
93
* //declare function to create Line
94
* Shape* createLine() {
95
* return new Line;
96
* }
97
*
98
* //register createLine
99
* //note: must put ShapeFactory::getInstance()->registerCreator("Line",
100
createLine) on the right
101
* //hand side, otherwise the compiler will consider it as a function
102
declaration
103
* const bool registeredLine =
104
ShapeFactory::getInstance()->registerCreator("Line", createLine);
105
*
106
* //Circle class
107
* class Circle : public Shape{
108
* ...
109
* };
110
*
111
* //declare function to create Circle
112
* Shape* createCircle() {
113
* return new Circle;
114
* }
115
*
116
* //register createCircle
117
* const bool registeredCircle =
118
ShapeFactory::getInstance()->registerCreator("Circle", createCircle);
119
*
120
* //create object by ident
121
* Line* line = ShapeFactory::getInstance()->createObject("Line");
122
* Circle* circle = ShapeFactory::getInstance()->createObject("Circle");
123
* @endcode
124
*
125
* Or the user can use predefined macro DECLARE_CREATOR and REGISTER_CREATOR
126
* @code
127
* //Shape class
128
* class Shape {
129
* ...
130
* };
131
*
132
* //instantiating a new object factory
133
* using ShapeFactory = GenericFactory<Shape>;
134
*
135
* //Line class
136
* class Line : public Shape{
137
* ...
138
* };
139
*
140
* //declare function using macro
141
* DECLARE_CREATOR(Shape, Line)
142
*
143
* //register using macro
144
* REGISTER_CREATOR(ShapeFactory, "Line", Line);
145
146
* //Circle class
147
* class Circle : public Shape{
148
* ...
149
* };
150
*
151
* //declare function using macro
152
* DECLARE_CREATOR(Shape, Circle)
153
*
154
* //register using macro
155
* REGISTER_CREATOR(ShapeFactory, "Circle", Circle);
156
* @endcode
157
*/
158
template
<
class
Object,
typename
IdentType = std::string,
159
typename
Creator = Object* (*)()>
160
class
GenericFactory
{
161
public
:
162
using
FactoryType =
GenericFactory<Object, IdentType, Creator>
;
163
using
CreatorMapType = std::map<IdentType, Creator>;
164
165
/**
166
* Returns an instance of object factory
167
* @return an instance of object factory
168
*/
169
static
FactoryType*
getInstance
() {
170
if
(instance_ == NULL) instance_ =
new
FactoryType;
171
return
instance_;
172
}
173
174
/**
175
* Registers a creator with a type identifier
176
* @return true if registration is succeed, otherwise return false
177
* @param id the identification of the concrete object
178
* @param creator the object responsible to create the concrete object
179
*/
180
bool
registerCreator
(
const
IdentType&
id
, Creator creator) {
181
return
creatorMap_.insert(CreatorMapType::value_type(
id
, creator)).second;
182
}
183
184
/**
185
* Unregisters the creator for the given type identifier. If the type
186
* identifier was previously registered, the function returns true.
187
* @return truethe type identifier was previously registered and the creator
188
* is removed, otherwise return false
189
* @param id the identification of the concrete object
190
*/
191
bool
unregisterCreator
(
const
IdentType&
id
) {
192
return
creatorMap_.erase(
id
) == 1;
193
}
194
195
/**
196
* Looks up the type identifier in the internal map. If it is found, it
197
* invokes the corresponding creator for the type identifier and returns its
198
* result.
199
* @return a pointer of the concrete object, return NULL if no creator is
200
* registed for creating this concrete object
201
* @param id the identification of the concrete object
202
*/
203
Object*
createObject
(
const
IdentType&
id
) {
204
typename
CreatorMapType::iterator i = creatorMap_.find(
id
);
205
if
(i != creatorMap_.end()) {
206
// invoke functor to create object
207
return
(i->second)();
208
}
else
{
209
return
NULL;
210
}
211
}
212
213
/**
214
* Returns all of the registed type identifiers
215
* @return all of the registed type identifiers
216
*/
217
std::vector<IdentType>
getIdents
() {
218
std::vector<IdentType> idents;
219
typename
CreatorMapType::iterator i;
220
221
for
(i = creatorMap_.begin(); i != creatorMap_.end(); ++i) {
222
idents.push_back(i->first);
223
}
224
225
return
idents;
226
}
227
228
public
:
229
static
FactoryType* instance_;
230
CreatorMapType creatorMap_;
231
};
232
233
/** write out all of the type identifiers to an output stream */
234
template
<
typename
O,
typename
I,
typename
C>
235
std::ostream& operator<<(std::ostream& o,
GenericFactory<O, I, C>
& factory) {
236
std::vector<I> idents;
237
std::vector<I>::iterator i;
238
239
idents = factory.
getIdents
();
240
241
o <<
"Avaliable type identifiers in this factory: "
<< std::endl;
242
for
(i = idents.begin(); i != idents.end(); ++i) {
243
o << *i << std::endl;
244
}
245
246
return
o;
247
}
248
249
// static template class member
250
template
<
class
Object,
typename
IdentType,
typename
Creator>
251
GenericFactory<Object, IdentType, Creator>*
252
GenericFactory<Object, IdentType, Creator>::instance_;
253
254
#define DECLARE_CREATOR(abstractObject, concreteObject) \
255
inline abstractObject* create##concreteObject() { return new concreteObject; }
256
257
#define REGISTER_CREATOR(factory, ident, concreteObject) \
258
const bool registered##concreteObject = \
259
factory::getInstance()->registerCreator(ident, create##concreteObject);
260
}
// namespace OpenMD
261
262
#endif
// UTIL_GENERICFACTORY_HPP
OpenMD::GenericFactory
GenericFactory is a template based Object Factory Factory pattern is used to define an interface for ...
Definition
GenericFactory.hpp:160
OpenMD::GenericFactory::getInstance
static FactoryType * getInstance()
Returns an instance of object factory.
Definition
GenericFactory.hpp:169
OpenMD::GenericFactory::unregisterCreator
bool unregisterCreator(const IdentType &id)
Unregisters the creator for the given type identifier.
Definition
GenericFactory.hpp:191
OpenMD::GenericFactory::createObject
Object * createObject(const IdentType &id)
Looks up the type identifier in the internal map.
Definition
GenericFactory.hpp:203
OpenMD::GenericFactory::registerCreator
bool registerCreator(const IdentType &id, Creator creator)
Registers a creator with a type identifier.
Definition
GenericFactory.hpp:180
OpenMD::GenericFactory::getIdents
std::vector< IdentType > getIdents()
Returns all of the registed type identifiers.
Definition
GenericFactory.hpp:217
OpenMD
This basic Periodic Table class was originally taken from the data.cpp file in OpenBabel.
Definition
ActionCorrFunc.cpp:63
utils
GenericFactory.hpp
Generated on
for OpenMD by
1.17.0