Reference documentation for deal.II version 9.1.1
\(\newcommand{\dealcoloneq}{\mathrel{\vcenter{:}}=}\)
parameter_handler.h
1 // ---------------------------------------------------------------------
2 //
3 // Copyright (C) 1998 - 2019 by the deal.II authors
4 //
5 // This file is part of the deal.II library.
6 //
7 // The deal.II library is free software; you can use it, redistribute
8 // it, and/or modify it under the terms of the GNU Lesser General
9 // Public License as published by the Free Software Foundation; either
10 // version 2.1 of the License, or (at your option) any later version.
11 // The full text of the license can be found in the file LICENSE.md at
12 // the top level directory of deal.II.
13 //
14 // ---------------------------------------------------------------------
15 
16 #ifndef dealii_parameter_handler_h
17 #define dealii_parameter_handler_h
18 
19 
20 #include <deal.II/base/config.h>
21 
22 #include <deal.II/base/exceptions.h>
23 #include <deal.II/base/patterns.h>
24 #include <deal.II/base/subscriptor.h>
25 
26 #include <boost/archive/basic_archive.hpp>
27 #include <boost/property_tree/ptree_fwd.hpp>
28 #include <boost/property_tree/ptree_serialization.hpp>
29 #include <boost/serialization/split_member.hpp>
30 
31 #include <map>
32 #include <memory>
33 #include <string>
34 #include <vector>
35 
36 DEAL_II_NAMESPACE_OPEN
37 
38 // forward declarations for interfaces and friendship
39 class LogStream;
41 
845 {
846 public:
852  {
857  Text = 1,
858 
862  LaTeX = 2,
867 
874  XML = 4,
875 
880  JSON = 5,
881 
886  ShortText = 193
887  };
888 
889 
890 
895 
901  virtual ~ParameterHandler() override = default;
902 
906  ParameterHandler(const ParameterHandler &) = delete;
907 
912  operator=(const ParameterHandler &) = delete;
913 
948  virtual void
949  parse_input(std::istream & input,
950  const std::string &filename = "input file",
951  const std::string &last_line = "",
952  const bool skip_undefined = false);
953 
997  virtual void
998  parse_input(const std::string &filename,
999  const std::string &last_line = "",
1000  const bool skip_undefined = false);
1001 
1010  virtual void
1011  parse_input_from_string(const std::string &s,
1012  const std::string &last_line = "",
1013  const bool skip_undefined = false);
1014 
1022  virtual void
1023  parse_input_from_xml(std::istream &input);
1024 
1032  virtual void
1033  parse_input_from_json(std::istream &input);
1034 
1038  void
1039  clear();
1040 
1041 
1061  void
1062  declare_entry(const std::string & entry,
1063  const std::string & default_value,
1064  const Patterns::PatternBase &pattern = Patterns::Anything(),
1065  const std::string & documentation = "");
1066 
1110  void
1111  add_action(const std::string & entry,
1112  const std::function<void(const std::string &value)> &action);
1113 
1123  template <class ParameterType>
1124  void
1125  add_parameter(const std::string & entry,
1126  ParameterType & parameter,
1127  const std::string & documentation = "",
1128  const Patterns::PatternBase &pattern =
1130 
1174  void
1175  declare_alias(const std::string &existing_entry_name,
1176  const std::string &alias_name,
1177  const bool alias_is_deprecated = false);
1178 
1182  void
1183  enter_subsection(const std::string &subsection);
1184 
1188  void
1189  leave_subsection();
1190 
1196  std::string
1197  get(const std::string &entry_string) const;
1198 
1209  std::string
1210  get(const std::vector<std::string> &entry_subsection_path,
1211  const std::string & entry_string) const;
1212 
1218  long int
1219  get_integer(const std::string &entry_string) const;
1220 
1229  long int
1230  get_integer(const std::vector<std::string> &entry_subsection_path,
1231  const std::string & entry_string) const;
1232 
1236  double
1237  get_double(const std::string &entry_name) const;
1238 
1245  double
1246  get_double(const std::vector<std::string> &entry_subsection_path,
1247  const std::string & entry_string) const;
1253  bool
1254  get_bool(const std::string &entry_name) const;
1255 
1264  bool
1265  get_bool(const std::vector<std::string> &entry_subsection_path,
1266  const std::string & entry_string) const;
1267 
1277  void
1278  set(const std::string &entry_name, const std::string &new_value);
1279 
1290  void
1291  set(const std::string &entry_name, const char *new_value);
1292 
1302  void
1303  set(const std::string &entry_name, const long int new_value);
1304 
1318  void
1319  set(const std::string &entry_name, const double new_value);
1320 
1330  void
1331  set(const std::string &entry_name, const bool new_value);
1332 
1333 
1393  std::ostream &
1394  print_parameters(std::ostream &out, const OutputStyle style) const;
1395 
1413  DEAL_II_DEPRECATED
1414  void
1415  print_parameters_section(std::ostream & out,
1416  const OutputStyle style,
1417  const unsigned int indent_level,
1418  const bool include_top_level_elements = false);
1419 
1425  void
1426  log_parameters(LogStream &out);
1427 
1437  void
1439 
1444  std::size_t
1445  memory_consumption() const;
1446 
1451  template <class Archive>
1452  void
1453  save(Archive &ar, const unsigned int version) const;
1454 
1459  template <class Archive>
1460  void
1461  load(Archive &ar, const unsigned int version);
1462 
1463  BOOST_SERIALIZATION_SPLIT_MEMBER()
1464 
1465 
1468  bool
1469  operator==(const ParameterHandler &prm2) const;
1470 
1480  std::string,
1481  << "The following entry already exists: " << arg1 << ".");
1486  std::string,
1487  std::string,
1488  << "The string <" << arg1
1489  << "> does not match the given pattern <" << arg2 << ">.");
1495  "You can't leave a subsection if you are already at the top level "
1496  "of the subsection hierarchy.");
1501  std::string,
1502  << "You can't ask for entry <" << arg1
1503  << "> you have not yet declared.");
1504 
1512  std::string,
1513  std::string,
1514  << "There are unequal numbers of 'subsection' and 'end' "
1515  "statements in the parameter file <"
1516  << arg1 << ">." << (arg2.size() > 0 ? "\n" + arg2 : ""));
1517 
1523  int,
1524  std::string,
1525  std::string,
1526  << "Line <" << arg1 << "> of file <" << arg2
1527  << ": There is "
1528  "no such subsection to be entered: "
1529  << arg3);
1530 
1537  int,
1538  std::string,
1539  std::string,
1540  << "Line <" << arg1 << "> of file <" << arg2 << ">: " << arg3);
1541 
1548  int,
1549  std::string,
1550  std::string,
1551  std::string,
1552  std::string,
1553  << "Line <" << arg1 << "> of file <" << arg2
1554  << ">:\n"
1555  " The entry value \n"
1556  << " " << arg3 << '\n'
1557  << " for the entry named\n"
1558  << " " << arg4 << '\n'
1559  << " does not match the given pattern:\n"
1560  << " " << arg5);
1561 
1568  "The provided file could not be parsed as a "
1569  "ParameterHandler description.");
1570 
1577  std::string,
1578  std::string,
1579  std::string,
1580  << " The entry value \n"
1581  << " " << arg1 << '\n'
1582  << " for the entry named\n"
1583  << " " << arg2 << '\n'
1584  << " does not match the given pattern:\n"
1585  << " " << arg3);
1586 
1595  int,
1596  std::string,
1597  std::string,
1598  << "Line <" << arg1 << "> of file <" << arg2
1599  << ">: This line "
1600  "contains an 'include' or 'INCLUDE' statement, but the given "
1601  "file to include <"
1602  << arg3 << "> cannot be opened.");
1603 
1605 private:
1610  static const char path_separator = '.';
1611 
1615  std::vector<std::string> subsection_path;
1616 
1625  std::unique_ptr<boost::property_tree::ptree> entries;
1626 
1632  std::vector<std::unique_ptr<const Patterns::PatternBase>> patterns;
1633 
1640  std::vector<std::function<void(const std::string &)>> actions;
1641 
1648  static std::string
1649  collate_path_string(const std::vector<std::string> &subsection_path);
1650 
1659  std::string
1660  get_current_path() const;
1661 
1666  std::string
1667  get_current_full_path(const std::string &name) const;
1668 
1673  std::string
1674  get_current_full_path(const std::vector<std::string> &sub_path,
1675  const std::string & name) const;
1676 
1695  void
1696  scan_line(std::string line,
1697  const std::string &input_filename,
1698  const unsigned int current_line_n,
1699  const bool skip_undefined);
1700 
1712  void
1714  const std::vector<std::string> &target_subsection_path,
1715  const OutputStyle style,
1716  const unsigned int indent_level,
1717  std::ostream & out) const;
1718 
1719  friend class MultipleParameterLoop;
1720 };
1721 
1722 
1723 
1940 class MultipleParameterLoop : public ParameterHandler
1941 {
1942 public:
1948  {
1949  public:
1954  virtual ~UserClass() = default;
1955 
1960  virtual void
1961  create_new(const unsigned int run_no) = 0;
1962 
1966  virtual void
1967  run(ParameterHandler &prm) = 0;
1968  };
1969 
1973  MultipleParameterLoop();
1974 
1979  virtual ~MultipleParameterLoop() override = default;
1980 
2002  virtual void
2003  parse_input(std::istream & input,
2004  const std::string &filename = "input file",
2005  const std::string &last_line = "",
2006  const bool skip_undefined = false) override;
2007 
2016 
2020  void
2021  loop(UserClass &uc);
2022 
2027  std::size_t
2028  memory_consumption() const;
2029 
2030 private:
2034  class Entry
2035  {
2036  public:
2043  {
2051  array
2052  };
2053 
2058  : type(array)
2059  {}
2060 
2066  Entry(const std::vector<std::string> &Path,
2067  const std::string & Name,
2068  const std::string & Value);
2069 
2073  void
2074  split_different_values();
2075 
2079  std::vector<std::string> subsection_path;
2080 
2084  std::string entry_name;
2085 
2089  std::string entry_value;
2090 
2095  std::vector<std::string> different_values;
2096 
2101 
2106  std::size_t
2107  memory_consumption() const;
2108  };
2109 
2113  std::vector<Entry> multiple_choices;
2114 
2119  unsigned int n_branches;
2120 
2124  void
2125  init_branches();
2126 
2133  void
2134  init_branches_current_section();
2135 
2139  void
2140  fill_entry_values(const unsigned int run_no);
2141 };
2142 
2143 
2144 // ---------------------- inline and template functions --------------------
2145 template <class Archive>
2146 inline void
2147 ParameterHandler::save(Archive &ar, const unsigned int) const
2148 {
2149  // Forward to serialization
2150  // function in the base class.
2151  ar &static_cast<const Subscriptor &>(*this);
2152 
2153  ar &*entries.get();
2154 
2155  std::vector<std::string> descriptions;
2156 
2157  for (const auto &pattern : patterns)
2158  descriptions.push_back(pattern->description());
2159 
2160  ar &descriptions;
2161 }
2162 
2163 
2164 template <class Archive>
2165 inline void
2166 ParameterHandler::load(Archive &ar, const unsigned int)
2167 {
2168  // Forward to serialization
2169  // function in the base class.
2170  ar &static_cast<Subscriptor &>(*this);
2171 
2172  ar &*entries.get();
2173 
2174  std::vector<std::string> descriptions;
2175  ar & descriptions;
2176 
2177  patterns.clear();
2178  for (const auto &description : descriptions)
2179  patterns.push_back(Patterns::pattern_factory(description));
2180 }
2181 
2182 
2183 template <class ParameterType>
2184 void
2185 ParameterHandler::add_parameter(const std::string & entry,
2186  ParameterType & parameter,
2187  const std::string & documentation,
2188  const Patterns::PatternBase &pattern)
2189 {
2190  static_assert(std::is_const<ParameterType>::value == false,
2191  "You tried to add a parameter using a type "
2192  "that is const. Use a non-const type.");
2193 
2194  declare_entry(entry,
2196  parameter, pattern.clone()),
2197  pattern,
2198  documentation);
2199 
2200  std::string path = get_current_full_path(entry);
2201  const unsigned int pattern_index =
2202  entries->get<unsigned int>(path + path_separator + "pattern");
2203 
2204  auto action = [&, pattern_index](const std::string &val) {
2206  val, patterns[pattern_index]->clone());
2207  };
2208  add_action(entry, action);
2209 }
2210 
2211 DEAL_II_NAMESPACE_CLOSE
2212 
2213 #endif
std::vector< Entry > multiple_choices
long int get_integer(const std::string &entry_string) const
void loop(ITERATOR begin, typename identity< ITERATOR >::type end, DOFINFO &dinfo, INFOBOX &info, const std::function< void(DOFINFO &, typename INFOBOX::CellInfo &)> &cell_worker, const std::function< void(DOFINFO &, typename INFOBOX::CellInfo &)> &boundary_worker, const std::function< void(DOFINFO &, DOFINFO &, typename INFOBOX::CellInfo &, typename INFOBOX::CellInfo &)> &face_worker, ASSEMBLER &assembler, const LoopControl &lctrl=LoopControl())
Definition: loop.h:443
static const char path_separator
#define DeclException2(Exception2, type1, type2, outsequence)
Definition: exceptions.h:541
void declare_entry(const std::string &entry, const std::string &default_value, const Patterns::PatternBase &pattern=Patterns::Anything(), const std::string &documentation="")
static ::ExceptionBase & ExcEntryAlreadyExists(std::string arg1)
static std::string collate_path_string(const std::vector< std::string > &subsection_path)
static ::ExceptionBase & ExcInvalidEntryForPatternXML(std::string arg1, std::string arg2, std::string arg3)
static ::ExceptionBase & ExcCannotOpenIncludeStatementFile(int arg1, std::string arg2, std::string arg3)
std::string get_current_path() const
static ::ExceptionBase & ExcEntryUndeclared(std::string arg1)
static T to_value(const std::string &s, const std::unique_ptr< Patterns::PatternBase > &p=Convert< T >::to_pattern())=delete
static ::ExceptionBase & ExcUnbalancedSubsections(std::string arg1, std::string arg2)
std::ostream & print_parameters(std::ostream &out, const OutputStyle style) const
void log_parameters(LogStream &out)
virtual void parse_input_from_string(const std::string &s, const std::string &last_line="", const bool skip_undefined=false)
virtual std::unique_ptr< PatternBase > clone() const =0
virtual void parse_input_from_json(std::istream &input)
void log_parameters_section(LogStream &out)
STL namespace.
std::vector< std::string > subsection_path
#define DeclException5( Exception5, type1, type2, type3, type4, type5, outsequence)
Definition: exceptions.h:613
void scan_line(std::string line, const std::string &input_filename, const unsigned int current_line_n, const bool skip_undefined)
static ::ExceptionBase & ExcValueDoesNotMatchPattern(std::string arg1, std::string arg2)
void load(Archive &ar, const unsigned int version)
std::vector< std::string > subsection_path
void add_parameter(const std::string &entry, ParameterType &parameter, const std::string &documentation="", const Patterns::PatternBase &pattern= *Patterns::Tools::Convert< ParameterType >::to_pattern())
void enter_subsection(const std::string &subsection)
virtual void parse_input_from_xml(std::istream &input)
static ::ExceptionBase & ExcInvalidXMLParameterFile()
static ::ExceptionBase & ExcCannotParseLine(int arg1, std::string arg2, std::string arg3)
double get_double(const std::string &entry_name) const
#define DeclException1(Exception1, type1, outsequence)
Definition: exceptions.h:518
std::string get_current_full_path(const std::string &name) const
#define DeclExceptionMsg(Exception, defaulttext)
Definition: exceptions.h:496
std::unique_ptr< boost::property_tree::ptree > entries
virtual void parse_input(std::istream &input, const std::string &filename="input file", const std::string &last_line="", const bool skip_undefined=false)
std::unique_ptr< PatternBase > pattern_factory(const std::string &description)
Definition: patterns.cc:136
bool get_bool(const std::string &entry_name) const
static ::ExceptionBase & ExcAlreadyAtTopLevel()
std::vector< std::unique_ptr< const Patterns::PatternBase > > patterns
void add_action(const std::string &entry, const std::function< void(const std::string &value)> &action)
void print_parameters_section(std::ostream &out, const OutputStyle style, const unsigned int indent_level, const bool include_top_level_elements=false)
void save(Archive &ar, const unsigned int version) const
void recursively_print_parameters(const std::vector< std::string > &target_subsection_path, const OutputStyle style, const unsigned int indent_level, std::ostream &out) const
std::vector< std::string > different_values
#define DeclException3(Exception3, type1, type2, type3, outsequence)
Definition: exceptions.h:564
std::size_t memory_consumption() const
static ::ExceptionBase & ExcInvalidEntryForPattern(int arg1, std::string arg2, std::string arg3, std::string arg4, std::string arg5)
std::vector< std::function< void(const std::string &)> > actions
virtual ~ParameterHandler() override=default
static ::ExceptionBase & ExcNoSubsection(int arg1, std::string arg2, std::string arg3)
void declare_alias(const std::string &existing_entry_name, const std::string &alias_name, const bool alias_is_deprecated=false)
ParameterHandler & operator=(const ParameterHandler &)=delete