Sort all includes in src/gromacs
[alexxy/gromacs.git] / src / gromacs / options / optionsvisitor.h
1 /*
2  * This file is part of the GROMACS molecular simulation package.
3  *
4  * Copyright (c) 2010,2011,2012,2014, by the GROMACS development team, led by
5  * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
6  * and including many others, as listed in the AUTHORS file in the
7  * top-level source directory and at http://www.gromacs.org.
8  *
9  * GROMACS is free software; you can redistribute it and/or
10  * modify it under the terms of the GNU Lesser General Public License
11  * as published by the Free Software Foundation; either version 2.1
12  * of the License, or (at your option) any later version.
13  *
14  * GROMACS is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
17  * Lesser General Public License for more details.
18  *
19  * You should have received a copy of the GNU Lesser General Public
20  * License along with GROMACS; if not, see
21  * http://www.gnu.org/licenses, or write to the Free Software Foundation,
22  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA.
23  *
24  * If you want to redistribute modifications to GROMACS, please
25  * consider that scientific software is very special. Version
26  * control is crucial - bugs must be traceable. We will be happy to
27  * consider code for inclusion in the official distribution, but
28  * derived work must not be called official GROMACS. Details are found
29  * in the README & COPYING files - if they are missing, get the
30  * official version at http://www.gromacs.org.
31  *
32  * To help us fund GROMACS development, we humbly ask that you cite
33  * the research papers on the package. Check out http://www.gromacs.org.
34  */
35 /*! \libinternal \file
36  * \brief
37  * Declares gmx::OptionsVisitor interface and supporting classes.
38  *
39  * \author Teemu Murtola <teemu.murtola@gmail.com>
40  * \inlibraryapi
41  * \ingroup module_options
42  */
43 #ifndef GMX_OPTIONS_OPTIONSVISITOR_H
44 #define GMX_OPTIONS_OPTIONSVISITOR_H
45
46 #include <cstddef>
47
48 #include <string>
49
50 #include "gromacs/options/abstractoption.h"
51 #include "gromacs/utility/common.h"
52
53 namespace gmx
54 {
55
56 class Options;
57
58 /*! \libinternal \brief
59  * Pure interface for visiting options in a Options object.
60  *
61  * \see OptionsIterator
62  *
63  * \inlibraryapi
64  * \ingroup module_options
65  */
66 class OptionsVisitor
67 {
68     public:
69         virtual ~OptionsVisitor() {}
70
71         /*! \brief
72          * Called for each subsection in Options.
73          */
74         virtual void visitSubSection(const Options &section) = 0;
75         /*! \brief
76          * Called for each option in Options.
77          */
78         virtual void visitOption(const OptionInfo &option) = 0;
79 };
80
81 /*! \libinternal \brief
82  * Abstract base class for visiting options of a particular type.
83  *
84  * \see OptionsIterator
85  * \see OptionsVisitor
86  *
87  * \inlibraryapi
88  * \ingroup module_options
89  */
90 template <class InfoType>
91 class OptionsTypeVisitor : public OptionsVisitor
92 {
93     public:
94         virtual ~OptionsTypeVisitor() {}
95
96         virtual void visitSubSection(const Options &section) = 0;
97         /*! \brief
98          * Called for each option of type \p InfoType.
99          */
100         virtual void visitOptionType(const InfoType &option) = 0;
101
102     private:
103         virtual void visitOption(const OptionInfo &option)
104         {
105             const InfoType *subtype = option.toType<InfoType>();
106             if (subtype != NULL)
107             {
108                 visitOptionType(*subtype);
109             }
110         }
111 };
112
113 /*! \libinternal \brief
114  * Decorator class for visiting options in a Options object.
115  *
116  * This class provides an interface for looping through subsections and
117  * options in a Options object.
118  *
119  * Typical use (loop over all options, iteratively descending into
120  * subsections):
121  * \code
122    class Visitor : public gmx::OptionsVisitor
123    {
124        public:
125            void visitSubSection(const Options &section)
126            {
127                OptionsIterator iterator(section);
128                iterator.acceptSubSections(this);
129                iterator.acceptOptions(this);
130            }
131
132            void visitOption(const OptionInfo &option)
133            {
134                // Do something.
135            }
136    }
137
138    Visitor().visitSubSection(options);
139  * \endcode
140  *
141  * \inlibraryapi
142  * \ingroup module_options
143  */
144 class OptionsIterator
145 {
146     public:
147         /*! \brief
148          * Creates an object for visiting options in a Options object.
149          */
150         explicit OptionsIterator(const Options &options);
151
152         /*! \brief
153          * Visits each subsection in the wrapped Options object.
154          */
155         void acceptSubSections(OptionsVisitor *visitor) const;
156         /*! \brief
157          * Visits each option in the wrapped Options object.
158          */
159         void acceptOptions(OptionsVisitor *visitor) const;
160
161     private:
162         //! The wrapped Options object.
163         const Options          &options_;
164
165         GMX_DISALLOW_COPY_AND_ASSIGN(OptionsIterator);
166 };
167
168 /*! \libinternal \brief
169  * Pure interface for visiting options in a Options object, allowing
170  * modifications.
171  *
172  * \see OptionsModifyingIterator
173  *
174  * \inlibraryapi
175  * \ingroup module_options
176  */
177 class OptionsModifyingVisitor
178 {
179     public:
180         virtual ~OptionsModifyingVisitor() {}
181
182         /*! \brief
183          * Called for each subsection in Options.
184          */
185         virtual void visitSubSection(Options *section) = 0;
186         /*! \brief
187          * Called for each option in Options.
188          */
189         virtual void visitOption(OptionInfo *option) = 0;
190 };
191
192 /*! \libinternal \brief
193  * Abstract base class for visiting options of a particular type, allowing
194  * modifications.
195  *
196  * \see OptionsModifyingIterator
197  * \see OptionsModifyingVisitor
198  *
199  * \inlibraryapi
200  * \ingroup module_options
201  */
202 template <class InfoType>
203 class OptionsModifyingTypeVisitor : public OptionsModifyingVisitor
204 {
205     public:
206         virtual ~OptionsModifyingTypeVisitor() {}
207
208         virtual void visitSubSection(Options *section) = 0;
209         /*! \brief
210          * Called for each option of type \p InfoType.
211          */
212         virtual void visitOptionType(InfoType *option) = 0;
213
214     private:
215         virtual void visitOption(OptionInfo *option)
216         {
217             InfoType *subtype = option->toType<InfoType>();
218             if (subtype != NULL)
219             {
220                 visitOptionType(subtype);
221             }
222         }
223 };
224
225 /*! \libinternal \brief
226  * Decorator class for visiting options in a Options object, allowing changes.
227  *
228  * This class works exactly like OptionsIterator, except that it uses
229  * OptionsModifyingVisitor interface, which allows modifying the options.
230  *
231  * \see OptionsIterator
232  *
233  * \inlibraryapi
234  * \ingroup module_options
235  */
236 class OptionsModifyingIterator
237 {
238     public:
239         /*! \brief
240          * Creates an object for visiting options in a Options object.
241          */
242         explicit OptionsModifyingIterator(Options *options);
243
244         /*! \brief
245          * Visits each subsection in the wrapped Options object.
246          */
247         void acceptSubSections(OptionsModifyingVisitor *visitor) const;
248         /*! \brief
249          * Visits each option in the wrapped Options object.
250          */
251         void acceptOptions(OptionsModifyingVisitor *visitor) const;
252
253     private:
254         //! The wrapped Options object.
255         Options                &options_;
256
257         GMX_DISALLOW_COPY_AND_ASSIGN(OptionsModifyingIterator);
258 };
259
260 } // namespace gmx
261
262 #endif