libMesh
Loading...
Searching...
No Matches
parameters.h
Go to the documentation of this file.
1// The libMesh Finite Element Library.
2// Copyright (C) 2002-2026 Benjamin S. Kirk, John W. Peterson, Roy H. Stogner
3
4// This library is free software; you can redistribute it and/or
5// modify it under the terms of the GNU Lesser General Public
6// License as published by the Free Software Foundation; either
7// version 2.1 of the License, or (at your option) any later version.
8
9// This library is distributed in the hope that it will be useful,
10// but WITHOUT ANY WARRANTY; without even the implied warranty of
11// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12// Lesser General Public License for more details.
13
14// You should have received a copy of the GNU Lesser General Public
15// License along with this library; if not, write to the Free Software
16// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17
18
19
20#ifndef LIBMESH_PARAMETERS_H
21#define LIBMESH_PARAMETERS_H
22
23// Local includes
24#include "libmesh/libmesh_common.h"
25#include "libmesh/reference_counted_object.h"
26#include "libmesh/print_trace.h"
27
28// C++ includes
29#include <cstddef>
30#include <map>
31#include <sstream>
32#include <string>
33#include <typeinfo>
34#include <vector>
35#include <memory>
36#include <set>
37#ifdef LIBMESH_HAVE_RTTI
38#include <typeinfo>
39#endif
40
41namespace libMesh
42{
47template<typename P>
48void print_helper(std::ostream & os, const P * param);
49
50template<typename P>
51void print_helper(std::ostream & os, const std::vector<P> * param);
52
53template<typename P>
54void print_helper(std::ostream & os, const std::vector<std::vector<P>> * param);
55
56template<typename P>
57void print_helper(std::ostream & os, const std::vector<std::vector<std::vector<P>>> * param);
58
59template<typename P1, typename P2, typename C, typename A>
60void print_helper(std::ostream & os, const std::map<P1, P2, C, A> * param);
61
62template <typename P, typename C, typename A>
63void print_helper(std::ostream & os, const std::set<P, C, A> * param);
64
75{
76public:
77
81 Parameters () = default;
82
87 Parameters (const Parameters &);
88
92 virtual ~Parameters () = default;
93
98 virtual Parameters & operator= (const Parameters & source);
99
105 virtual Parameters & operator+= (const Parameters & source);
106
114 template <typename T>
115 bool have_parameter (std::string_view) const;
116
121 template <typename T>
122 const T & get (std::string_view) const;
123
129 template <typename T>
130 void insert (const std::string &);
131
138 template <typename T>
139 T & set (const std::string &);
140
145 virtual void set_attributes(const std::string &, bool /*inserted_only*/) {}
146
150 void remove (std::string_view);
151
155 std::size_t n_parameters () const { return _values.size(); }
156
157#ifdef LIBMESH_HAVE_RTTI
161 template <typename T>
162 unsigned int n_parameters () const;
163#endif // LIBMESH_HAVE_RTTI
164
168 virtual void clear ();
169
173 void print (std::ostream & os=libMesh::out) const;
174
178 class Value : public ReferenceCountedObject<Value>
179 {
180 public:
181
185 virtual ~Value() = default;
186
187#ifdef LIBMESH_HAVE_RTTI
192 virtual const std::type_info & type_info () const = 0;
193
198 virtual std::string type () const = 0;
199#endif // LIBMESH_HAVE_RTTI
200
205 virtual void print(std::ostream &) const = 0;
206
211 virtual std::unique_ptr<Value> clone () const = 0;
212 };
213
218 template <typename T>
219 class Parameter : public Value
220 {
221 public:
222
226 const T & get () const { return _value; }
227
231 T & set () { return _value; }
232
233#ifdef LIBMESH_HAVE_RTTI
237 virtual const std::type_info & type_info () const override;
238
242 virtual std::string type () const override;
243#endif // LIBMESH_HAVE_RTTI
244
248 virtual void print(std::ostream &) const override;
249
253 virtual std::unique_ptr<Value> clone () const override;
254
255 private:
260 };
261
265 typedef std::map<std::string, std::unique_ptr<Value>, std::less<>> map_type;
266
270 typedef map_type::iterator iterator;
271
275 typedef map_type::const_iterator const_iterator;
276
280 iterator begin();
281
285 const_iterator begin() const;
286
290 iterator end();
291
295 const_iterator end() const;
296
297protected:
298
303};
304
305// ------------------------------------------------------------
306// Parameters::Parameter<> class inline methods
307
308// These only work with Run-Time Type Information, even though
309// typeid(T) *should* be determinable at compile time regardless...
310#ifdef LIBMESH_HAVE_RTTI
311template <typename T>
312inline
313const std::type_info & Parameters::Parameter<T>::type_info () const
314{
315 return typeid(T);
316}
317
318template <typename T>
319inline
321{
322 return demangle(type_info().name());
323}
324#endif
325
326template <typename T>
327inline
328void Parameters::Parameter<T>::print (std::ostream & os) const
329{
330 // Call helper function overloaded for basic scalar and vector types
331 print_helper(os, static_cast<const T *>(&_value));
332}
333
334template <typename T>
335inline
336std::unique_ptr<Parameters::Value> Parameters::Parameter<T>::clone () const
337{
338 auto copy = std::make_unique<Parameter<T>>();
339
340 copy->_value = this->_value; // assign value
341
342 return copy; // as unique_ptr to base class
343}
344
345
346// ------------------------------------------------------------
347// Parameters class inline methods
348inline
350{
351 _values.clear();
352}
353
354
355
356inline
358{
359 this->Parameters::clear();
360 *this += source;
361
362 return *this;
363}
364
365inline
367{
368 // Overwrite each value (if it exists) or create a new entry
369 for (const auto & [key, value] : source._values)
370 _values[key] = value->clone();
371
372 return *this;
373}
374
375inline
377{
378 // calls assignment operator
379 *this = p;
380}
381
382
383
384inline
385void Parameters::print (std::ostream & os) const
386{
388
389 os << "Name\t Type\t Value\n"
390 << "---------------------\n";
391 while (it != _values.end())
392 {
393 os << " " << it->first
394#ifdef LIBMESH_HAVE_RTTI
395 << "\t " << it->second->type()
396#endif // LIBMESH_HAVE_RTTI
397 << "\t "; it->second->print(os);
398 os << '\n';
399
400 ++it;
401 }
402}
403
404
405
406// Declare this now that Parameters::print() is defined.
407// By declaring this early we can use it in subsequent
408// methods. Required for gcc-4.0.2 -- 11/30/2005, BSK
409inline
410std::ostream & operator << (std::ostream & os, const Parameters & p)
411{
412 p.print(os);
413 return os;
414}
415
416
417
418template <typename T>
419inline
420bool Parameters::have_parameter (std::string_view name) const
421{
422 Parameters::const_iterator it = _values.find(name);
423
424 if (it != _values.end())
425 {
426#ifdef LIBMESH_HAVE_RTTI
427
428 if (dynamic_cast<const Parameter<T> *>(it->second.get()))
429 return true;
430
431#else // !LIBMESH_HAVE_RTTI
432
433 // cast_ptr will simply do a static_cast here when RTTI is not
434 // enabled, and it will return a non-nullptr regardless of
435 // whether or not the cast actually succeeds.
436 libmesh_warning("Parameters::have_parameter() may return false positives when RTTI is not enabled.");
437
438 if (cast_ptr<const Parameter<T> *>(it->second.get()))
439 return true;
440
441#endif
442 }
443
444 return false;
445}
446
447
448
449template <typename T>
450inline
451const T & Parameters::get (std::string_view name) const
452{
453 if (!this->have_parameter<T>(name))
454 {
455 std::ostringstream oss;
456
457 oss << "ERROR: no";
458#ifdef LIBMESH_HAVE_RTTI
459 oss << ' ' << demangle(typeid(T).name());
460#endif
461 oss << " parameter named \""
462 << name << "\" found.\n\n"
463 << "Known parameters:\n"
464 << *this;
465
466 libmesh_error_msg(oss.str());
467 }
468
469 Parameters::const_iterator it = _values.find(name);
470
471 libmesh_assert(it != _values.end());
472 libmesh_assert(it->second);
473
474 // Get pointer to derived type
475 auto ptr = cast_ptr<Parameter<T> *>(it->second.get());
476
477 // Return const reference
478 return ptr->get();
479}
480
481template <typename T>
482inline
483void Parameters::insert (const std::string & name)
484{
485 if (!this->have_parameter<T>(name))
486 _values[name] = std::make_unique<Parameter<T>>();
487
488 set_attributes(name, true);
489}
490
491
492template <typename T>
493inline
494T & Parameters::set (const std::string & name)
495{
496 if (!this->have_parameter<T>(name))
497 _values[name] = std::make_unique<Parameter<T>>();
498
499 set_attributes(name, false);
500
501 // Get pointer to existing or just-added entry
502 auto ptr = cast_ptr<Parameter<T> *>(_values[name].get());
503
504 // Return writeable reference
505 return ptr->set();
506}
507
508inline
509void Parameters::remove (std::string_view name)
510{
511 Parameters::iterator it = _values.find(name);
512
513 if (it != _values.end())
514 _values.erase(it);
515}
516
517
518
519#ifdef LIBMESH_HAVE_RTTI
520template <typename T>
521inline
522unsigned int Parameters::n_parameters () const
523{
524 unsigned int cnt = 0;
525
526 for (const auto & pr : _values)
527 if (dynamic_cast<Parameter<T> *>(pr.second.get()))
528 cnt++;
529
530 return cnt;
531}
532#endif
533
534inline
536{
537 return _values.begin();
538}
539
540inline
542{
543 return _values.begin();
544}
545
546inline
548{
549 return _values.end();
550}
551
552inline
554{
555 return _values.end();
556}
557
558//non-member scalar print function
559template<typename P>
560void print_helper(std::ostream & os, const P * param)
561{
562 os << *param;
563}
564
565template<>
566inline
567void print_helper(std::ostream & os, const char * param)
568{
569 // Specialization so that we don't print out unprintable characters
570 os << static_cast<int>(*param);
571}
572
573template<>
574inline
575void print_helper(std::ostream & os, const unsigned char * param)
576{
577 // Specialization so that we don't print out unprintable characters
578 os << static_cast<int>(*param);
579}
580
581//non-member vector print function
582template<typename P>
583void print_helper(std::ostream & os, const std::vector<P> * param)
584{
585 for (const auto & p : *param)
586 os << p << " ";
587}
588
589//non-member vector<vector> print function
590template<typename P>
591void print_helper(std::ostream & os, const std::vector<std::vector<P>> * param)
592{
593 for (const auto & pv : *param)
594 for (const auto & p : pv)
595 os << p << " ";
596}
597
598//non-member vector<vector<vector>> print function
599template<typename P>
600void print_helper(std::ostream & os, const std::vector<std::vector<std::vector<P>>> * param)
601{
602 for (const auto & pvv : *param)
603 for (const auto & pv : pvv)
604 for (const auto & p : pv)
605 os << p << " ";
606}
607
608//non-member map print function
609template<typename P1, typename P2, typename C, typename A>
610void print_helper(std::ostream & os, const std::map<P1, P2, C, A> * param)
611{
612 os << '{';
613 std::size_t sz = param->size();
614 for (auto KV : *param)
615 {
616 os << '\'' << KV.first << "\' => \'" << KV.second << '\'';
617 if (--sz)
618 os << ", ";
619 }
620 os << '}';
621}
622
623//non-member set print function
624template<typename P, typename C, typename A>
625void print_helper(std::ostream & os, const std::set<P, C, A> * param)
626{
627 for (const auto & p : *param)
628 os << p << " ";
629}
630
631
632} // namespace libMesh
633
634#endif // LIBMESH_PARAMETERS_H
Concrete definition of a parameter value for a specified type.
Definition parameters.h:220
virtual std::unique_ptr< Value > clone() const override
Clone this value.
Definition parameters.h:336
T _value
Stored parameter value.
Definition parameters.h:259
virtual const std::type_info & type_info() const override
std::type_info for type of parameter stored.
Definition parameters.h:313
virtual std::string type() const override
String identifying the type of parameter stored.
Definition parameters.h:320
virtual void print(std::ostream &) const override
Prints the parameter value to the specified stream.
Definition parameters.h:328
Abstract definition of a parameter value.
Definition parameters.h:179
virtual const std::type_info & type_info() const =0
std::type_info for type of parameter stored.
virtual ~Value()=default
Destructor.
virtual std::string type() const =0
String identifying the type of parameter stored.
virtual void print(std::ostream &) const =0
Prints the parameter value to the specified stream.
virtual std::unique_ptr< Value > clone() const =0
Clone this value.
This class provides the ability to map between arbitrary, user-defined strings and several data types...
Definition parameters.h:75
map_type::iterator iterator
Parameter map iterator.
Definition parameters.h:270
void remove(std::string_view)
Removes the specified parameter from the list, if it exists.
Definition parameters.h:509
std::size_t n_parameters() const
Definition parameters.h:155
bool have_parameter(std::string_view) const
Definition parameters.h:420
iterator begin()
Iterator pointing to the beginning of the set of parameters.
Definition parameters.h:535
void insert(const std::string &)
Inserts a new Parameter into the object but does not return a writable reference.
Definition parameters.h:483
map_type _values
Data structure to map names with values.
Definition parameters.h:302
map_type::const_iterator const_iterator
Constant parameter map iterator.
Definition parameters.h:275
virtual void clear()
Clears internal data structures & frees any allocated memory.
Definition parameters.h:349
T & set(const std::string &)
Definition parameters.h:494
void print(std::ostream &os=libMesh::out) const
Prints the contents, by default to libMesh::out.
Definition parameters.h:385
iterator end()
Iterator pointing to the end of the set of parameters.
Definition parameters.h:547
virtual void set_attributes(const std::string &, bool)
Overridable function to set any extended attributes for classes inheriting from this class.
Definition parameters.h:145
virtual Parameters & operator=(const Parameters &source)
Assignment operator.
Definition parameters.h:357
virtual Parameters & operator+=(const Parameters &source)
Addition/Assignment operator.
Definition parameters.h:366
virtual ~Parameters()=default
Destructor.
const T & get(std::string_view) const
Definition parameters.h:451
std::map< std::string, std::unique_ptr< Value >, std::less<> > map_type
The type of the map that we store internally.
Definition parameters.h:265
Parameters()=default
Default constructor.
This class implements reference counting.
The libMesh namespace provides an interface to certain functionality in the library.
std::string demangle(const char *name)
Mostly system independent demangler.
libmesh_assert(ctx)
std::ostream & operator<<(std::ostream &os, const OrderWrapper &order)
Overload stream operators.
Definition fe_type.h:182
void print_helper(std::ostream &os, const P *param)
Helper functions for printing scalar, vector, vector<vector> and vector<vector<vector>> types.
Definition parameters.h:560
OStreamProxy out
Tnew cast_ptr(Told *oldvar)
static const bool value
Definition xdr_io.C:55