Skip to content
Snippets Groups Projects
Commit cefd6bfb authored by René Fritze's avatar René Fritze
Browse files

introduce new ConfigContainer as ParameterContainer replacement

parent 16ccff2a
No related branches found
No related tags found
No related merge requests found
#ifndef DUNE_STUFF_CONFIGCONTAINER_HH_INCLUDED
#define DUNE_STUFF_CONFIGCONTAINER_HH_INCLUDED
#include <dune/stuff/deprecated.hh> // ensure DUNE_DEPRECATED is defined properly
#include "logging.hh"
#include "filesystem.hh"
#include "misc.hh"
#include "validation.hh"
#include <boost/format.hpp>
#include <dune/common/parametertree.hh>
#include <dune/common/parametertreeparser.hh>
#include <dune/common/exceptions.hh>
namespace Stuff {
class ConfigContainer
{
private:
template <typename T, class Validator>
T getValidValue(std::string name, T def, const ValidatorInterface<T, Validator> validator)
{
T val = tree_.get(name, def);
if (validator(val))
return val;
std::stringstream ss;
validator.print(ss);
DUNE_THROW(Dune::ParameterInvalid, ss.str());
}
public:
ConfigContainer(const Dune::ParameterTree& tree)
: warning_output_(false)
, tree_(tree)
{
}
ConfigContainer()
: warning_output_(true)
{
}
void readCommandLine(int argc, char** argv)
{
if (argc < 2) {
boost::format usage("usage: %s parameter.file *[section.key:override-value]");
DUNE_THROW(Dune::Exception, (usage % argv[0]).str());
}
Dune::ParameterTreeParser::readINITree(argv[1], tree_);
for (int i = 1; i < argc; ++i) {
auto tokens = Stuff::stringTokenize(argv[i], ":");
if (tokens.size() > 2)
tree_[tokens[0]] = tokens[1];
}
} // ReadCommandLine
/** \brief passthrough to underlying Dune::Parameter
* \param useDbgStream
* needs to be set to false when using this function in Logging::Create,
* otherwise an assertion will will cause streams aren't available yet
**/
template <typename T>
T get(std::string name, T def, bool useDbgStream = true)
{
return get(name, def, Stuff::ValidateAny<T>(), useDbgStream);
}
//! hack around the "string" is no string issue
std::string get(std::string name, const char* def, bool useDbgStream = true)
{
return get(name, std::string(def), Stuff::ValidateAny<std::string>(), useDbgStream);
}
template <typename T, class Validator>
T get(std::string name, T def, const ValidatorInterface<T, Validator> validator,
bool UNUSED_UNLESS_DEBUG(useDbgStream) = true)
{
if (not validator(def))
DUNE_THROW(Dune::ParameterInvalid, "default value invalid");
#ifndef NDEBUG
if (warning_output_ && !tree_.hasKey(name)) {
if (useDbgStream)
Logger().Dbg() << "WARNING: using default value for parameter \"" << name << "\"" << std::endl;
else
std::cerr << "WARNING: using default value for parameter \"" << name << "\"" << std::endl;
}
#endif // ifndef NDEBUG
try {
return getValidValue(name, def, validator);
} catch (Dune::ParameterInvalid& p) {
std::cerr << boost::format("Parameter %s invalid: %s\n") % name % p.what();
}
return def;
} // getParam
//! hack around the "string" is no string issue
template <class Validator>
std::string get(std::string name, const char* def, const ValidatorInterface<std::string, Validator> validator,
bool useDbgStream = true)
{
return get<std::string, Validator>(name, def, validator, useDbgStream);
}
private:
bool warning_output_;
Dune::ParameterTree tree_;
};
// ! global ConfigContainer instance
ConfigContainer& Config()
{
static ConfigContainer parameters;
return parameters;
}
} // end namespace Stuff
#endif // DUNE_STUFF_CONFIGCONTAINER_HH_INCLUDED
/** Copyright (c) 2012, Rene Milk
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this
* list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright notice,
* this list of conditions and the following disclaimer in the documentation
* and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
* ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* The views and conclusions contained in the software and documentation are those
* of the authors and should not be interpreted as representing official policies,
* either expressed or implied, of the FreeBSD Project.
**/
#ifndef DUNE_STUFF_VALIDATION_HH
#define DUNE_STUFF_VALIDATION_HH
#include <ostream>
#include <string>
#include <boost/format.hpp>
#include "misc.hh"
namespace Stuff {
/** \brief Base class for all Validators
* the idea is from dune-fem, only our class is an actual interface
**/
template <class T, class Derived>
class ValidatorInterface
{
public:
bool operator()(const T& value) const
{
return asImp()(value);
}
std::string msg() const
{
return asImp().msg();
}
void print(std::ostream& out) const
{
out << asImp().msg();
}
protected:
inline const Derived& asImp() const
{
return static_cast<const Derived&>(*this);
}
inline Derived& asImp()
{
return static_cast<Derived&>(*this);
}
};
// ! a class usable as a default validator
template <class T>
class ValidateAny : public Stuff::ValidatorInterface<T, ValidateAny<T>>
{
typedef ValidateAny<T> ThisType;
typedef ValidatorInterface<T, ThisType> BaseType;
public:
inline ValidateAny()
{
}
inline ValidateAny(const ThisType&)
{
}
inline bool operator()(const T&) const
{
return true;
}
std::string msg() const
{
return "ValidateAny: all values should be valid... \n\n";
}
};
// ! validates arg iff in given list
template <class T, class ListImp = std::vector<T>>
class ValidateInList : public Stuff::ValidatorInterface<T, ValidateInList<T, ListImp>>
{
typedef ValidateInList<T, ListImp> ThisType;
typedef ValidatorInterface<T, ThisType> BaseType;
typedef ListImp ListType;
ListType valid_list_;
public:
ValidateInList(const ListType& valid_list)
: valid_list_(valid_list)
{
}
inline bool operator()(const T& val) const
{
return std::find(valid_list_.begin(), valid_list_.end(), val) != valid_list_.end();
}
std::string msg() const
{
return "ValidateInList: checked Parameter was not in valid list\n\n";
}
};
//! validate arg iff less than value, obviously
template <class T>
class ValidateLess : public ValidatorInterface<T, ValidateLess<T>>
{
public:
ValidateLess(const T& max)
: max_(max)
{
}
inline bool operator()(const T& val) const
{
return val < max_;
}
std::string msg() const
{
return (boost::format("given value was invalid: not less than %s") % toString(max_)).str();
}
private:
const T max_;
};
//! validate iff not Validator(arg)
template <class T, class Validator>
class ValidateInverse : public ValidatorInterface<T, ValidateInverse<T, Validator>>
{
public:
ValidateInverse(const Validator validator = Validator())
: validator_(validator)
{
}
inline bool operator()(const T& val) const
{
return !validator_(val);
}
std::string msg() const
{
return "Inverse condition failed";
}
private:
const Validator validator_;
};
//! validate arg iff arg \in [min,max]
template <class T>
class ValidateInterval : public ValidatorInterface<T, ValidateInterval<T>>
{
public:
ValidateInterval(const T& min, const T& max)
: min_(min)
, max_(max)
{
}
inline bool operator()(const T& val) const
{
return min_(val) && ValidateInverse<T, ValidateLess<T>>(val)(max_);
}
std::string msg() const
{
return "given value was invalid: value not in given interval";
}
private:
const ValidateInverse<T, ValidateLess<T>> min_;
const T max_;
};
template <class T>
struct ValidateNone : public ValidateInverse<T, ValidateAny<T>>
{
};
} // end namesapce Stuff
template <class T, class Validator>
std::ostream operator<<(std::ostream& out, const Stuff::ValidatorInterface<T, Validator>& validator)
{
return out << validator.msg();
}
#endif // DUNE_STUFF_VALIDATION_HH
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment