Browse Source

Merge branch 'refactorFormulas'

Conflicts:
	src/counterexamples/SMTMinimalCommandSetGenerator.h
	src/storm.cpp

Former-commit-id: f65836b10d
main
masawei 11 years ago
parent
commit
4f5b0b5949
  1. 20
      src/counterexamples/MILPMinimalLabelSetGenerator.h
  2. 167
      src/counterexamples/PathBasedSubsystemGenerator.h
  3. 41
      src/counterexamples/SMTMinimalCommandSetGenerator.h
  4. 73
      src/formula/AbstractFormulaChecker.h
  5. 31
      src/formula/Csl.h
  6. 31
      src/formula/Csl/AbstractCslFormula.h
  7. 83
      src/formula/Csl/AbstractNoBoundOperator.h
  8. 129
      src/formula/Csl/And.h
  9. 106
      src/formula/Csl/Ap.h
  10. 120
      src/formula/Csl/Eventually.h
  11. 122
      src/formula/Csl/Globally.h
  12. 120
      src/formula/Csl/Next.h
  13. 116
      src/formula/Csl/Not.h
  14. 125
      src/formula/Csl/Or.h
  15. 121
      src/formula/Csl/ProbabilisticBoundOperator.h
  16. 115
      src/formula/Csl/ProbabilisticNoBoundOperator.h
  17. 118
      src/formula/Csl/SteadyStateBoundOperator.h
  18. 100
      src/formula/Csl/SteadyStateNoBoundOperator.h
  19. 97
      src/formula/Csl/TimeBoundedEventually.h
  20. 111
      src/formula/Csl/TimeBoundedUntil.h
  21. 125
      src/formula/Csl/Until.h
  22. 150
      src/formula/Ltl/And.h
  23. 129
      src/formula/Ltl/Ap.h
  24. 146
      src/formula/Ltl/BoundedEventually.h
  25. 163
      src/formula/Ltl/BoundedUntil.h
  26. 140
      src/formula/Ltl/Eventually.h
  27. 142
      src/formula/Ltl/Globally.h
  28. 140
      src/formula/Ltl/Next.h
  29. 136
      src/formula/Ltl/Not.h
  30. 141
      src/formula/Ltl/Or.h
  31. 157
      src/formula/Ltl/Until.h
  32. 16
      src/formula/Ltl/visitor/AbstractLtlFormulaVisitor.cpp
  33. 72
      src/formula/Ltl/visitor/AbstractLtlFormulaVisitor.h
  34. 42
      src/formula/Prctl.h
  35. 83
      src/formula/Prctl/AbstractNoBoundOperator.h
  36. 31
      src/formula/Prctl/AbstractPrctlFormula.h
  37. 129
      src/formula/Prctl/And.h
  38. 106
      src/formula/Prctl/Ap.h
  39. 126
      src/formula/Prctl/BoundedEventually.h
  40. 141
      src/formula/Prctl/BoundedNaryUntil.h
  41. 131
      src/formula/Prctl/BoundedUntil.h
  42. 110
      src/formula/Prctl/CumulativeReward.h
  43. 120
      src/formula/Prctl/Eventually.h
  44. 122
      src/formula/Prctl/Globally.h
  45. 111
      src/formula/Prctl/InstantaneousReward.h
  46. 120
      src/formula/Prctl/Next.h
  47. 116
      src/formula/Prctl/Not.h
  48. 125
      src/formula/Prctl/Or.h
  49. 139
      src/formula/Prctl/ProbabilisticBoundOperator.h
  50. 115
      src/formula/Prctl/ProbabilisticNoBoundOperator.h
  51. 117
      src/formula/Prctl/ReachabilityReward.h
  52. 132
      src/formula/Prctl/RewardBoundOperator.h
  53. 108
      src/formula/Prctl/RewardNoBoundOperator.h
  54. 91
      src/formula/Prctl/SteadyStateReward.h
  55. 125
      src/formula/Prctl/Until.h
  56. 49
      src/formula/PrctlFormulaChecker.h
  57. 92
      src/formula/abstract/AbstractFormula.h
  58. 164
      src/formula/abstract/And.h
  59. 84
      src/formula/abstract/Ap.h
  60. 151
      src/formula/abstract/BoundedEventually.h
  61. 175
      src/formula/abstract/BoundedNaryUntil.h
  62. 182
      src/formula/abstract/BoundedUntil.h
  63. 101
      src/formula/abstract/CumulativeReward.h
  64. 125
      src/formula/abstract/Eventually.h
  65. 126
      src/formula/abstract/Globally.h
  66. 41
      src/formula/abstract/IOptimizingOperator.h
  67. 101
      src/formula/abstract/InstantaneousReward.h
  68. 128
      src/formula/abstract/Next.h
  69. 122
      src/formula/abstract/Not.h
  70. 72
      src/formula/abstract/OptimizingOperator.h
  71. 161
      src/formula/abstract/Or.h
  72. 194
      src/formula/abstract/PathBoundOperator.h
  73. 160
      src/formula/abstract/PathNoBoundOperator.h
  74. 114
      src/formula/abstract/ProbabilisticBoundOperator.h
  75. 104
      src/formula/abstract/ProbabilisticNoBoundOperator.h
  76. 106
      src/formula/abstract/RewardBoundOperator.h
  77. 103
      src/formula/abstract/RewardNoBoundOperator.h
  78. 174
      src/formula/abstract/StateBoundOperator.h
  79. 126
      src/formula/abstract/StateNoBoundOperator.h
  80. 77
      src/formula/abstract/SteadyStateBoundOperator.h
  81. 76
      src/formula/abstract/SteadyStateNoBoundOperator.h
  82. 62
      src/formula/abstract/SteadyStateReward.h
  83. 107
      src/formula/abstract/TimeBoundedEventually.h
  84. 112
      src/formula/abstract/TimeBoundedOperator.h
  85. 149
      src/formula/abstract/TimeBoundedUntil.h
  86. 159
      src/formula/abstract/Until.h
  87. 155
      src/modelchecker/csl/AbstractModelChecker.h
  88. 105
      src/modelchecker/csl/SparseMarkovAutomatonCslModelChecker.h
  89. 56
      src/modelchecker/ltl/AbstractModelChecker.h
  90. 181
      src/modelchecker/prctl/AbstractModelChecker.h
  91. 83
      src/modelchecker/prctl/SparseDtmcPrctlModelChecker.h
  92. 192
      src/modelchecker/prctl/SparseMdpPrctlModelChecker.h
  93. 4
      src/models/Dtmc.h
  94. 241
      src/parser/CslParser.cpp
  95. 40
      src/parser/CslParser.h
  96. 6
      src/parser/LtlFileParser.cpp
  97. 21
      src/parser/LtlFileParser.h
  98. 191
      src/parser/LtlParser.cpp
  99. 34
      src/parser/LtlParser.h
  100. 12
      src/parser/PrctlFileParser.cpp

20
src/counterexamples/MILPMinimalLabelSetGenerator.h

@ -985,38 +985,38 @@ namespace storm {
* @param formulaPtr A pointer to a safety formula. The outermost operator must be a probabilistic bound operator with a strict upper bound. The nested
* formula can be either an unbounded until formula or an eventually formula.
*/
static void computeCounterexample(storm::prism::Program const& program, storm::models::Mdp<T> const& labeledMdp, storm::property::prctl::AbstractPrctlFormula<double> const* formulaPtr) {
static void computeCounterexample(storm::prism::Program const& program, storm::models::Mdp<T> const& labeledMdp, std::shared_ptr<storm::properties::prctl::AbstractPrctlFormula<double>> const & formulaPtr) {
std::cout << std::endl << "Generating minimal label counterexample for formula " << formulaPtr->toString() << std::endl;
// First, we need to check whether the current formula is an Until-Formula.
storm::property::prctl::ProbabilisticBoundOperator<double> const* probBoundFormula = dynamic_cast<storm::property::prctl::ProbabilisticBoundOperator<double> const*>(formulaPtr);
auto probBoundFormula = std::dynamic_pointer_cast<storm::properties::prctl::ProbabilisticBoundOperator<double>>(formulaPtr);
if (probBoundFormula == nullptr) {
LOG4CPLUS_ERROR(logger, "Illegal formula " << probBoundFormula->toString() << " for counterexample generation.");
throw storm::exceptions::InvalidPropertyException() << "Illegal formula " << probBoundFormula->toString() << " for counterexample generation.";
}
if (probBoundFormula->getComparisonOperator() != storm::property::ComparisonType::LESS && probBoundFormula->getComparisonOperator() != storm::property::ComparisonType::LESS_EQUAL) {
if (probBoundFormula->getComparisonOperator() != storm::properties::ComparisonType::LESS && probBoundFormula->getComparisonOperator() != storm::properties::ComparisonType::LESS_EQUAL) {
LOG4CPLUS_ERROR(logger, "Illegal comparison operator in formula " << probBoundFormula->toString() << ". Only upper bounds are supported for counterexample generation.");
throw storm::exceptions::InvalidPropertyException() << "Illegal comparison operator in formula " << probBoundFormula->toString() << ". Only upper bounds are supported for counterexample generation.";
}
bool strictBound = !(probBoundFormula->getComparisonOperator() == storm::property::ComparisonType::LESS);
bool strictBound = !(probBoundFormula->getComparisonOperator() == storm::properties::ComparisonType::LESS);
// Now derive the probability threshold we need to exceed as well as the phi and psi states. Simultaneously, check whether the formula is of a valid shape.
double bound = probBoundFormula->getBound();
storm::property::prctl::AbstractPathFormula<double> const& pathFormula = probBoundFormula->getPathFormula();
std::shared_ptr<storm::properties::prctl::AbstractPathFormula<double>> pathFormula = probBoundFormula->getChild();
storm::storage::BitVector phiStates;
storm::storage::BitVector psiStates;
storm::modelchecker::prctl::SparseMdpPrctlModelChecker<T> modelchecker(labeledMdp);
try {
storm::property::prctl::Until<double> const& untilFormula = dynamic_cast<storm::property::prctl::Until<double> const&>(pathFormula);
auto untilFormula = std::dynamic_pointer_cast<storm::properties::prctl::Until<double>>(pathFormula);
phiStates = untilFormula.getLeft().check(modelchecker);
psiStates = untilFormula.getRight().check(modelchecker);
phiStates = untilFormula->getLeft()->check(modelchecker);
psiStates = untilFormula->getRight()->check(modelchecker);
} catch (std::bad_cast const&) {
// If the nested formula was not an until formula, it remains to check whether it's an eventually formula.
try {
storm::property::prctl::Eventually<double> const& eventuallyFormula = dynamic_cast<storm::property::prctl::Eventually<double> const&>(pathFormula);
auto eventuallyFormula = std::dynamic_pointer_cast<storm::properties::prctl::Eventually<double>>(pathFormula);
phiStates = storm::storage::BitVector(labeledMdp.getNumberOfStates(), true);
psiStates = eventuallyFormula.getChild().check(modelchecker);
psiStates = eventuallyFormula->getChild()->check(modelchecker);
} catch (std::bad_cast const&) {
// If the nested formula is neither an until nor a finally formula, we throw an exception.
throw storm::exceptions::InvalidPropertyException() << "Formula nested inside probability bound operator must be an until or eventually formula for counterexample generation.";

167
src/counterexamples/PathBasedSubsystemGenerator.h

@ -272,138 +272,6 @@ public:
LOG4CPLUS_DEBUG(logger, "Discovery done.");
}
/*!
*
*//*
template <typename T>
static void doBackwardsSearch(storm::storage::SparseMatrix<T> const& transMat, storm::storage::BitVector& initStates, storm::storage::BitVector& subSysStates, storm::storage::BitVector& terminalStates, storm::storage::BitVector& allowedStates, std::vector<T>& probabilities, std::vector<uint_fast64_t>& shortestPath, T& probability) {
std::multiset<std::pair<uint_fast64_t, T>, CompareStates<T> > activeSet;
// resize and init distances
const std::pair<uint_fast64_t, T> initDistances(0, (T) -1);
std::vector<std::pair<uint_fast64_t, T>> distances(transMat.getColumnCount(), initDistances);
//since the transition matrix only gives a means to iterate over successors and not over predecessors and there is no Transpose for the matrix
//GraphTransitions is used
storm::models::GraphTransitions<T> backTrans(transMat, false);
//First store all allowed predecessors of target states that are not in the subsystem
for(storm::storage::BitVector::constIndexIterator target = terminalStates.begin(); target != terminalStates.end(); ++target) {
// if there is a terminal state that is an initial state then prob == 1 and return
if(initStates.get(*target)){
distances[*target].getColumn() = *target;
distances[*target].getValue() = (T) 1;
return;
}
//iterate over predecessors
for(auto iter = backTrans.beginStateSuccessorsIterator(*target); iter != backTrans.endStateSuccessorsIterator(*target); iter++) {
//only use if allowed and not in subsys and not terminal
if(allowedStates.get(*iter) && !subSysStates.get(*iter) && !terminalStates.get(*iter)) {
//new state?
if(distances[*iter].getValue() == (T) -1) {
// save as discovered and push into active set
distances[*iter].getColumn() = *target; //successor
distances[*iter].getValue() = transMat.getValue(*iter, *target); //prob of shortest path
activeSet.insert(std::pair<uint_fast64_t, T>(*iter, probabilities[*iter])); //prob of reaching some terminal state from pred.
}
else {
// state was already discovered
// is this the better transition?
if(distances[*iter].getValue() > transMat.getValue(*iter, *target)) {
distances[*iter].getColumn() = *target;
distances[*iter].getValue() = transMat.getValue(*iter, *target);
}
}
}
}
}
//Now store all allowed predecessors of subsystem states that are not subsystem states themselves
for(storm::storage::BitVector::constIndexIterator sysState = subSysStates.begin(); sysState != subSysStates.end(); ++sysState) {
//iterate over predecessors
for(auto iter = backTrans.beginStateSuccessorsIterator(*sysState); iter != backTrans.endStateSuccessorsIterator(*sysState); iter++) {
//only use if allowed and not in subsys and not terminal
if(allowedStates.get(*iter) && !subSysStates.get(*iter) && !terminalStates.get(*iter)) {
//new state?
if(distances[*iter].getValue() == (T) -1) {
// save as discovered and push into active set
distances[*iter].getColumn() = *sysState; //successor
distances[*iter].getValue() = transMat.getValue(*iter, *sysState); //prob of shortest path
activeSet.insert(std::pair<uint_fast64_t, T>(*iter, probabilities[*iter])); //prob of reaching some terminal state from pred.
}
else {
// state was already discovered
// is this the better transition?
if(distances[*iter].getValue() > transMat.getValue(*iter, *sysState)) {
distances[*iter].getColumn() = *sysState;
distances[*iter].getValue() = transMat.getValue(*iter, *sysState);
}
}
}
}
}
LOG4CPLUS_DEBUG(logger, "Initialized.");
// Do the backwards search
std::pair<uint_fast64_t, T> state;
uint_fast64_t activeState;
while(!activeSet.empty()) {
// copy here since using a reference leads to segfault
state = *(--activeSet.end());
activeState = state.getColumn();
activeSet.erase(--activeSet.end());
//stop on the first subsys/init state
if(initStates.get(activeState) || subSysStates.get(activeState)) break;
// If this is a subSys or terminal state, do not consider its incoming transitions, since all relevant ones have already been considered
if(!terminalStates.get(activeState) && !subSysStates.get(activeState)) {
//iterate over predecessors
for(auto iter = backTrans.beginStateSuccessorsIterator(activeState); iter != backTrans.endStateSuccessorsIterator(activeState); iter++) {
//only if transition is not "virtual" and no selfloop
if(*iter != activeState && transMat.getValue(*iter, activeState) != (T) 0) {
//new state?
if(distances[*iter].getValue() == (T) -1) {
// save as discovered and push into active set
distances[*iter].getColumn() = activeState;
distances[*iter].getValue() = transMat.getValue(*iter, activeState) * distances[activeState].getValue();
activeSet.insert(std::pair<uint_fast64_t, T>(*iter, probabilities[*iter]));
}
else {
// state was already discovered
// is this the better transition?
if(distances[*iter].getValue() < transMat.getValue(*iter, activeState) * distances[activeState].getValue()) {
distances[*iter].getColumn() = activeState;
distances[*iter].getValue() = transMat.getValue(*iter, activeState) * distances[activeState].getValue();
}
}
}
}
}
}
//get path probability
probability = distances[activeState].getValue();
if(probability == (T) -1) probability = 1;
// iterate over the successors until reaching the end of the finite path
shortestPath.push_back(activeState);
activeState = distances[activeState].getColumn();
while(!terminalStates.get(activeState) && !subSysStates.get(activeState)) {
shortestPath.push_back(activeState);
activeState = distances[activeState].getColumn();
}
shortestPath.push_back(activeState);
}
*/
/*!
*
*/
@ -507,7 +375,7 @@ public:
/*!
*
*/
static storm::models::Dtmc<T> computeCriticalSubsystem(storm::models::Dtmc<T> & model, storm::property::prctl::AbstractStateFormula<T> const& stateFormula) {
static storm::models::Dtmc<T> computeCriticalSubsystem(storm::models::Dtmc<T> & model, std::shared_ptr<storm::properties::prctl::AbstractStateFormula<T>> const & stateFormula) {
//-------------------------------------------------------------
// 1. Strip and handle formulas
@ -525,27 +393,22 @@ public:
// init bit vector to contain the subsystem
storm::storage::BitVector subSys(model.getNumberOfStates());
storm::property::prctl::AbstractPathFormula<T> const* pathFormulaPtr;
T bound = 0;
// Strip bound operator
storm::property::prctl::ProbabilisticBoundOperator<T> const* boundOperator = dynamic_cast<storm::property::prctl::ProbabilisticBoundOperator<T> const*>(&stateFormula);
std::shared_ptr<storm::properties::prctl::ProbabilisticBoundOperator<T>> boundOperator = std::dynamic_pointer_cast<storm::properties::prctl::ProbabilisticBoundOperator<T>>(stateFormula);
if(boundOperator == nullptr){
LOG4CPLUS_ERROR(logger, "No path bound operator at formula root.");
return model.getSubDtmc(subSys);
}
bound = boundOperator->getBound();
storm::property::prctl::AbstractPathFormula<T> const& abstractPathFormula = boundOperator->getPathFormula();
pathFormulaPtr = &abstractPathFormula;
T bound = boundOperator->getBound();
std::shared_ptr<storm::properties::prctl::AbstractPathFormula<T>> pathFormula = boundOperator->getChild();
// get "init" labeled states
storm::storage::BitVector initStates = model.getLabeledStates("init");
//get real prob for formula
logger.getAppender("mainFileAppender")->setThreshold(log4cplus::WARN_LOG_LEVEL);
std::vector<T> trueProbs = pathFormulaPtr->check(modelCheck, false);
std::vector<T> trueProbs = pathFormula->check(modelCheck, false);
logger.getAppender("mainFileAppender")->setThreshold(log4cplus::INFO_LOG_LEVEL);
T trueProb = 0;
@ -559,22 +422,22 @@ public:
storm::storage::BitVector allowedStates;
storm::storage::BitVector targetStates;
storm::property::prctl::Eventually<T> const* eventually = dynamic_cast<storm::property::prctl::Eventually<T> const*>(pathFormulaPtr);
storm::property::prctl::Globally<T> const* globally = dynamic_cast<storm::property::prctl::Globally<T> const*>(pathFormulaPtr);
storm::property::prctl::Until<T> const* until = dynamic_cast<storm::property::prctl::Until<T> const*>(pathFormulaPtr);
if(eventually != nullptr) {
targetStates = eventually->getChild().check(modelCheck);
std::shared_ptr<storm::properties::prctl::Eventually<T>> eventually = std::dynamic_pointer_cast<storm::properties::prctl::Eventually<T>>(pathFormula);
std::shared_ptr<storm::properties::prctl::Globally<T>> globally = std::dynamic_pointer_cast<storm::properties::prctl::Globally<T>>(pathFormula);
std::shared_ptr<storm::properties::prctl::Until<T>> until = std::dynamic_pointer_cast<storm::properties::prctl::Until<T>>(pathFormula);
if(eventually.get() != nullptr) {
targetStates = eventually->getChild()->check(modelCheck);
allowedStates = storm::storage::BitVector(targetStates.size(), true);
}
else if(globally != nullptr){
else if(globally.get() != nullptr){
//eventually reaching a state without property visiting only states with property
allowedStates = globally->getChild().check(modelCheck);
allowedStates = globally->getChild()->check(modelCheck);
targetStates = storm::storage::BitVector(allowedStates);
targetStates.complement();
}
else if(until != nullptr) {
allowedStates = until->getLeft().check(modelCheck);
targetStates = until->getRight().check(modelCheck);
else if(until.get() != nullptr) {
allowedStates = until->getLeft()->check(modelCheck);
targetStates = until->getRight()->check(modelCheck);
}
else {
LOG4CPLUS_ERROR(logger, "Strange path formula. Can't decipher.");

41
src/counterexamples/SMTMinimalCommandSetGenerator.h

@ -1785,42 +1785,41 @@ namespace storm {
#ifdef STORM_HAVE_Z3
std::cout << std::endl << "Generating minimal label counterexample for formula " << formulaPtr->toString() << std::endl;
// First, we need to check whether the current formula is an Until-Formula.
storm::property::prctl::ProbabilisticBoundOperator<double> const* probBoundFormula = dynamic_cast<storm::property::prctl::ProbabilisticBoundOperator<double> const*>(formulaPtr);
if (probBoundFormula == nullptr) {
std::shared_ptr<storm::properties::prctl::ProbabilisticBoundOperator<double>> probBoundFormula = std::dynamic_pointer_cast<storm::properties::prctl::ProbabilisticBoundOperator<double>>(formulaPtr);
if (probBoundFormula.get() == nullptr) {
LOG4CPLUS_ERROR(logger, "Illegal formula " << probBoundFormula->toString() << " for counterexample generation.");
throw storm::exceptions::InvalidPropertyException() << "Illegal formula " << probBoundFormula->toString() << " for counterexample generation.";
}
// Check whether we were given an upper bound, because counterexample generation is limited to this case.
if (probBoundFormula->getComparisonOperator() != storm::property::ComparisonType::LESS && probBoundFormula->getComparisonOperator() != storm::property::ComparisonType::LESS_EQUAL) {
if (probBoundFormula->getComparisonOperator() != storm::properties::ComparisonType::LESS && probBoundFormula->getComparisonOperator() != storm::properties::ComparisonType::LESS_EQUAL) {
LOG4CPLUS_ERROR(logger, "Illegal comparison operator in formula " << probBoundFormula->toString() << ". Only upper bounds are supported for counterexample generation.");
throw storm::exceptions::InvalidPropertyException() << "Illegal comparison operator in formula " << probBoundFormula->toString() << ". Only upper bounds are supported for counterexample generation.";
}
bool strictBound = probBoundFormula->getComparisonOperator() == storm::property::ComparisonType::LESS;
bool strictBound = probBoundFormula->getComparisonOperator() == storm::properties::ComparisonType::LESS;
// Now derive the probability threshold we need to exceed as well as the phi and psi states. Simultaneously, check whether the formula is of a valid shape.
double bound = probBoundFormula->getBound();
storm::property::prctl::AbstractPathFormula<double> const& pathFormula = probBoundFormula->getPathFormula();
std::shared_ptr<storm::properties::prctl::AbstractPathFormula<double>> pathFormula = probBoundFormula->getPathFormula();
storm::storage::BitVector phiStates;
storm::storage::BitVector psiStates;
storm::modelchecker::prctl::SparseMdpPrctlModelChecker<T> modelchecker(labeledMdp);
try {
storm::property::prctl::Until<double> const& untilFormula = dynamic_cast<storm::property::prctl::Until<double> const&>(pathFormula);
phiStates = untilFormula.getLeft().check(modelchecker);
psiStates = untilFormula.getRight().check(modelchecker);
} catch (std::bad_cast const&) {
std::shared_ptr<storm::properties::prctl::Until<double>> untilFormula = std::dynamic_pointer_cast<storm::properties::prctl::Until<double>>(pathFormula);
if(untilFormula.get() != nullptr) {
phiStates = untilFormula->getLeft()->check(modelchecker);
psiStates = untilFormula->getRight()->check(modelchecker);
} if (std::dynamic_pointer_cast<storm::properties::prctl::Eventually<double>>(pathFormula).get() != nullptr) {
// If the nested formula was not an until formula, it remains to check whether it's an eventually formula.
try {
storm::property::prctl::Eventually<double> const& eventuallyFormula = dynamic_cast<storm::property::prctl::Eventually<double> const&>(pathFormula);
phiStates = storm::storage::BitVector(labeledMdp.getNumberOfStates(), true);
psiStates = eventuallyFormula.getChild().check(modelchecker);
} catch (std::bad_cast const&) {
// If the nested formula is neither an until nor a finally formula, we throw an exception.
LOG4CPLUS_ERROR(logger, "Formula nested inside probability bound operator must be an until or eventually formula for counterexample generation.");
throw storm::exceptions::InvalidPropertyException() << "Formula nested inside probability bound operator must be an until or eventually formula for counterexample generation.";
}
std::shared_ptr<storm::properties::prctl::Eventually<double>> eventuallyFormula = std::dynamic_pointer_cast<storm::properties::prctl::Eventually<double>>(pathFormula);
phiStates = storm::storage::BitVector(labeledMdp.getNumberOfStates(), true);
psiStates = eventuallyFormula->getChild()->check(modelchecker);
} else {
// If the nested formula is neither an until nor a finally formula, we throw an exception.
throw storm::exceptions::InvalidPropertyException() << "Formula nested inside probability bound operator must be an until or eventually formula for counterexample generation.";
}
// Delegate the actual computation work to the function of equal name.

73
src/formula/AbstractFormulaChecker.h

@ -1,73 +0,0 @@
#ifndef STORM_FORMULA_ABSTRACTFORMULACHECKER_H_
#define STORM_FORMULA_ABSTRACTFORMULACHECKER_H_
namespace storm {
namespace property {
template <class T> class AbstractFormulaChecker;
} //namespace property
} //namespace storm
#include "src/formula/abstract/AbstractFormula.h"
namespace storm {
namespace property {
/*!
* @brief Base class for all formula checkers.
*
* A formula checker is used to check if a given formula is valid in some
* logic. Hence, this pure virtual base class should be subclassed for
* every logic we support.
*
* Every subclass must implement validate(). It gets a pointer to an
* AbstractFormula object and should return if the subtree represented by
* this formula is valid in the logic.
*
* Usually, this will be implemented like this:
* @code
* if (
* dynamic_cast<const And<T>*>(formula) ||
* dynamic_cast<const Not<T>*>(formula) ||
* dynamic_cast<const Or<T>*>(formula)
* ) {
* return formula->validate(*this);
* } else return false;
* @endcode
*
* Every formula class implements a validate() method itself which calls
* validate() on the given checker for every child in the formula tree.
*
* If the formula structure is not an actual tree, but an directed acyclic
* graph, the shared subtrees will be checked twice. If we have directed
* cycles, we will have infinite recursions.
*/
template <class T>
class AbstractFormulaChecker {
public:
/*!
* Virtual destructor
* To ensure that the right destructor is called
*/
virtual ~AbstractFormulaChecker() {
//intentionally left empty
}
/*!
* @brief Checks if the given formula is valid in some logic.
*
* Every subclass must implement this method and check, if the
* formula object is valid in the logic of the subclass.
*
* @param formula A pointer to some formula object.
* @return true iff the formula is valid.
*/
virtual bool validate(const storm::property::abstract::AbstractFormula<T>* formula) const = 0;
};
} // namespace property
} // namespace storm
#endif

31
src/formula/Csl.h

@ -1,31 +0,0 @@
/*
* Csl.h
*
* Created on: 19.04.2013
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_CSL_H_
#define STORM_FORMULA_CSL_H_
#include "src/modelchecker/csl/ForwardDeclarations.h"
#include "Csl/And.h"
#include "Csl/Ap.h"
#include "Csl/Next.h"
#include "Csl/Not.h"
#include "Csl/Or.h"
#include "Csl/ProbabilisticNoBoundOperator.h"
#include "Csl/ProbabilisticBoundOperator.h"
#include "Csl/SteadyStateNoBoundOperator.h"
#include "Csl/SteadyStateBoundOperator.h"
#include "Csl/Until.h"
#include "Csl/Eventually.h"
#include "Csl/Globally.h"
#include "Csl/TimeBoundedEventually.h"
#include "Csl/TimeBoundedUntil.h"
#include "modelchecker/csl/AbstractModelChecker.h"
#endif /* STORM_FORMULA_CSL_H_ */

31
src/formula/Csl/AbstractCslFormula.h

@ -1,31 +0,0 @@
/*
* AbstractCslFormula.h
*
* Created on: 19.04.2013
* Author: Thomas Heinemann
*/
#ifndef ABSTRACTCSLFORMULA_H_
#define ABSTRACTCSLFORMULA_H_
#include "src/formula/abstract/AbstractFormula.h"
namespace storm {
namespace property {
namespace csl {
/*!
* Abstract base class for all CSL root formulas.
*/
template <class T>
class AbstractCslFormula : public virtual storm::property::abstract::AbstractFormula<T>{
public:
virtual ~AbstractCslFormula() {
// Intentionally left empty
}
};
} /* namespace csl */
} /* namespace property */
} /* namespace storm */
#endif /* ABSTRACTCSLFORMULA_H_ */

83
src/formula/Csl/AbstractNoBoundOperator.h

@ -1,83 +0,0 @@
/*
* AbstractNoBoundOperator.h
*
* Created on: 16.04.2013
* Author: thomas
*/
#ifndef STORM_FORMULA_CSL_ABSTRACTNOBOUNDOPERATOR_H_
#define STORM_FORMULA_CSL_ABSTRACTNOBOUNDOPERATOR_H_
#include "AbstractCslFormula.h"
#include "src/formula/abstract/IOptimizingOperator.h"
namespace storm {
namespace property {
namespace csl {
template <class T>
class AbstractNoBoundOperator;
/*!
* @brief Interface class for model checkers that support PathNoBoundOperator.
*
* All model checkers that support the formula class NoBoundOperator must inherit
* this pure virtual class.
*/
template <class T>
class INoBoundOperatorModelChecker {
public:
/*!
* @brief Evaluates NoBoundOperator formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkNoBoundOperator(const AbstractNoBoundOperator<T>& obj) const = 0;
};
/*!
* Interface class for all CSL No Bound operators.
*/
template <class T>
class AbstractNoBoundOperator: public AbstractCslFormula<T>,
public virtual storm::property::abstract::IOptimizingOperator {
public:
AbstractNoBoundOperator() {
// Intentionally left empty
}
virtual ~AbstractNoBoundOperator() {
// Intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @note This function is not implemented in this class.
* @returns a new AND-object that is identical the called object.
*/
virtual AbstractNoBoundOperator<T>* clone() const = 0;
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @note This function is not implemented in this class.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::csl::AbstractModelChecker<T>& modelChecker, bool qualitative=false) const = 0;
};
} /* namespace csl */
} /* namespace property */
} /* namespace storm */
#endif /* STORM_FORMULA_CSL_ABSTRACTNOBOUNDOPERATOR_H_ */

129
src/formula/Csl/And.h

@ -1,129 +0,0 @@
/*
* And.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_CSL_AND_H_
#define STORM_FORMULA_CSL_AND_H_
#include "AbstractStateFormula.h"
#include "src/formula/abstract/And.h"
#include "src/formula/AbstractFormulaChecker.h"
#include "src/modelchecker/csl/ForwardDeclarations.h"
#include <string>
namespace storm {
namespace property {
namespace csl {
template <class T> class And;
/*!
* @brief Interface class for model checkers that support And.
*
* All model checkers that support the formula class And must inherit
* this pure virtual class.
*/
template <class T>
class IAndModelChecker {
public:
/*!
* @brief Evaluates And formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual storm::storage::BitVector checkAnd(const And<T>& obj) const = 0;
};
/*!
* @brief
* Class for an abstract formula tree with AND node as root.
*
* Has two Abstract state formulas as sub formulas/trees.
*
* As AND is commutative, the order is \e theoretically not important, but will influence the order in which
* the model checker works.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractStateFormula
* @see AbstractCslFormula
*/
template <class T>
class And : public storm::property::abstract::And<T, AbstractStateFormula<T>>, public AbstractStateFormula<T> {
public:
/*!
* Empty constructor.
* Will create an AND-node without subnotes. Will not represent a complete formula!
*/
And() {
//intentionally left empty
}
/*!
* Constructor.
* Creates an AND note with the parameters as subtrees.
*
* @param left The left sub formula
* @param right The right sub formula
*/
And(AbstractStateFormula<T>* left, AbstractStateFormula<T>* right)
: storm::property::abstract::And<T, AbstractStateFormula<T>>(left, right) {
//intentionally left empty
}
/*!
* Destructor.
*
* The subtrees are deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*/
virtual ~And() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new AND-object that is identical the called object.
*/
virtual AbstractStateFormula<T>* clone() const override {
And<T>* result = new And();
if (this->leftIsSet()) {
result->setLeft(this->getLeft().clone());
}
if (this->rightIsSet()) {
result->setRight(this->getRight().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A bit vector indicating all states that satisfy the formula represented by the called object.
*/
virtual storm::storage::BitVector check(const storm::modelchecker::csl::AbstractModelChecker<T>& modelChecker) const override {
return modelChecker.template as<IAndModelChecker>()->checkAnd(*this);
}
};
} //namespace csl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_CSL_AND_H_ */

106
src/formula/Csl/Ap.h

@ -1,106 +0,0 @@
/*
* Ap.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_CSL_AP_H_
#define STORM_FORMULA_CSL_AP_H_
#include "AbstractStateFormula.h"
#include "src/formula/abstract/Ap.h"
#include "src/formula/AbstractFormulaChecker.h"
#include "src/modelchecker/csl/ForwardDeclarations.h"
namespace storm {
namespace property {
namespace csl {
template <class T> class Ap;
/*!
* @brief Interface class for model checkers that support Ap.
*
* All model checkers that support the formula class Ap must inherit
* this pure virtual class.
*/
template <class T>
class IApModelChecker {
public:
/*!
* @brief Evaluates Ap formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual storm::storage::BitVector checkAp(const Ap<T>& obj) const = 0;
};
/*!
* @brief
* Class for an abstract formula tree with atomic proposition as root.
*
* This class represents the leaves in the formula tree.
*
* @see AbstractCslFormula
* @see AbstractStateFormula
*/
template <class T>
class Ap : public storm::property::abstract::Ap<T>,
public AbstractStateFormula<T> {
public:
/*!
* Constructor
*
* Creates a new atomic proposition leaf, with the label Ap
*
* @param ap The string representing the atomic proposition
*/
Ap(std::string ap)
: storm::property::abstract::Ap<T>(ap) {
// Intentionally left empty
}
/*!
* Destructor.
* At this time, empty...
*/
virtual ~Ap() {
// Intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new AND-object that is identical the called object.
*/
virtual AbstractStateFormula<T>* clone() const override {
return new Ap(this->getAp());
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A bit vector indicating all states that satisfy the formula represented by the called object.
*/
virtual storm::storage::BitVector check(const storm::modelchecker::csl::AbstractModelChecker<T>& modelChecker) const override {
return modelChecker.template as<IApModelChecker>()->checkAp(*this);
}
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_CSL_AP_H_ */

120
src/formula/Csl/Eventually.h

@ -1,120 +0,0 @@
/*
* Next.h
*
* Created on: 26.12.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_CSL_EVENTUALLY_H_
#define STORM_FORMULA_CSL_EVENTUALLY_H_
#include "src/formula/abstract/Eventually.h"
#include "src/formula/Csl/AbstractPathFormula.h"
#include "src/formula/Csl/AbstractStateFormula.h"
#include "src/modelchecker/csl/ForwardDeclarations.h"
namespace storm {
namespace property {
namespace csl {
template <class T> class Eventually;
/*!
* @brief Interface class for model checkers that support Eventually.
*
* All model checkers that support the formula class Eventually must inherit
* this pure virtual class.
*/
template <class T>
class IEventuallyModelChecker {
public:
/*!
* @brief Evaluates Eventually formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkEventually(const Eventually<T>& obj, bool qualitative) const = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with an Eventually node as root.
*
* Has one Abstract state formula as sub formula/tree.
*
* @par Semantics
* The formula holds iff eventually \e child holds.
*
* The subtree is seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to nullptr before deletion)
*
* @see AbstractPathFormula
* @see AbstractCslFormula
*/
template <class T>
class Eventually : public storm::property::abstract::Eventually<T, AbstractStateFormula<T>>,
public AbstractPathFormula<T> {
public:
/*!
* Empty constructor
*/
Eventually() {
// Intentionally left empty
}
/*!
* Constructor
*
* @param child The child node
*/
Eventually(AbstractStateFormula<T>* child)
: storm::property::abstract::Eventually<T, AbstractStateFormula<T>>(child) {
}
/*!
* Constructor.
*
* Also deletes the subtree.
* (this behaviour can be prevented by setting the subtrees to nullptr before deletion)
*/
virtual ~Eventually() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new Eventually-object that is identical the called object.
*/
virtual AbstractPathFormula<T>* clone() const override {
Eventually<T>* result = new Eventually<T>();
if (this->childIsSet()) {
result->setChild(this->getChild().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::csl::AbstractModelChecker<T>& modelChecker, bool qualitative) const override {
return modelChecker.template as<IEventuallyModelChecker>()->checkEventually(*this, qualitative);
}
};
} //namespace csl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_CSL_EVENTUALLY_H_ */

122
src/formula/Csl/Globally.h

@ -1,122 +0,0 @@
/*
* Next.h
*
* Created on: 26.12.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_CSL_GLOBALLY_H_
#define STORM_FORMULA_CSL_GLOBALLY_H_
#include "src/formula/abstract/Globally.h"
#include "AbstractPathFormula.h"
#include "AbstractStateFormula.h"
#include "src/formula/AbstractFormulaChecker.h"
#include "src/modelchecker/csl/ForwardDeclarations.h"
namespace storm {
namespace property {
namespace csl {
template <class T> class Globally;
/*!
* @brief Interface class for model checkers that support Globally.
*
* All model checkers that support the formula class Globally must inherit
* this pure virtual class.
*/
template <class T>
class IGloballyModelChecker {
public:
/*!
* @brief Evaluates Globally formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkGlobally(const Globally<T>& obj, bool qualitative) const = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with a Globally node as root.
*
* Has one Abstract state formula as sub formula/tree.
*
* @par Semantics
* The formula holds iff globally \e child holds.
*
* The subtree is seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to nullptr before deletion)
*
* @see AbstractPathFormula
* @see AbstractCslFormula
*/
template <class T>
class Globally : public storm::property::abstract::Globally<T, AbstractStateFormula<T>>,
public AbstractPathFormula<T> {
public:
/*!
* Empty constructor
*/
Globally() {
//intentionally left empty
}
/*!
* Constructor
*
* @param child The child node
*/
Globally(AbstractStateFormula<T>* child)
: storm::property::abstract::Globally<T, AbstractStateFormula<T>>(child) {
//intentionally left empty
}
/*!
* Constructor.
*
* Also deletes the subtree.
* (this behaviour can be prevented by setting the subtrees to nullptr before deletion)
*/
virtual ~Globally() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new Globally-object that is identical the called object.
*/
virtual AbstractPathFormula<T>* clone() const override {
Globally<T>* result = new Globally<T>();
if (this->childIsSet()) {
result->setChild(this->getChild().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::csl::AbstractModelChecker<T>& modelChecker, bool qualitative) const override {
return modelChecker.template as<IGloballyModelChecker>()->checkGlobally(*this, qualitative);
}
};
} //namespace csl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_CSL_GLOBALLY_H_ */

120
src/formula/Csl/Next.h

@ -1,120 +0,0 @@
/*
* Next.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_CSL_NEXT_H_
#define STORM_FORMULA_CSL_NEXT_H_
#include "AbstractPathFormula.h"
#include "AbstractStateFormula.h"
#include "src/formula/abstract/Next.h"
#include "src/formula/AbstractFormulaChecker.h"
namespace storm {
namespace property {
namespace csl {
template <class T> class Next;
/*!
* @brief Interface class for model checkers that support Next.
*
* All model checkers that support the formula class Next must inherit
* this pure virtual class.
*/
template <class T>
class INextModelChecker {
public:
/*!
* @brief Evaluates Next formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkNext(const Next<T>& obj, bool qualitative) const = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with a Next node as root.
*
* Has two Abstract state formulas as sub formulas/trees.
*
* @par Semantics
* The formula holds iff in the next step, \e child holds
*
* The subtree is seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractPathFormula
* @see AbstractCslFormula
*/
template <class T>
class Next : public storm::property::abstract::Next<T, AbstractStateFormula<T>>,
public AbstractPathFormula<T> {
public:
/*!
* Empty constructor
*/
Next() {
//intentionally left empty
}
/*!
* Constructor
*
* @param child The child node
*/
Next(AbstractStateFormula<T>* child)
: storm::property::abstract::Next<T, AbstractStateFormula<T>>(child) {
//intentionally left empty
}
/*!
* Constructor.
*
* Also deletes the subtree.
* (this behaviour can be prevented by setting the subtrees to NULL before deletion)
*/
virtual ~Next() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new BoundedUntil-object that is identical the called object.
*/
virtual AbstractPathFormula<T>* clone() const override {
Next<T>* result = new Next<T>();
if (this->childIsSet()) {
result->setChild(this->getChild().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::csl::AbstractModelChecker<T>& modelChecker, bool qualitative) const override {
return modelChecker.template as<INextModelChecker>()->checkNext(*this, qualitative);
}
};
} //namespace csl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_CSL_NEXT_H_ */

116
src/formula/Csl/Not.h

@ -1,116 +0,0 @@
/*
* Not.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_CSL_NOT_H_
#define STORM_FORMULA_CSL_NOT_H_
#include "AbstractStateFormula.h"
#include "src/formula/abstract/Not.h"
#include "src/formula/AbstractFormulaChecker.h"
#include "src/modelchecker/csl/ForwardDeclarations.h"
namespace storm {
namespace property {
namespace csl {
template <class T> class Not;
/*!
* @brief Interface class for model checkers that support Not.
*
* All model checkers that support the formula class Not must inherit
* this pure virtual class.
*/
template <class T>
class INotModelChecker {
public:
/*!
* @brief Evaluates Not formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual storm::storage::BitVector checkNot(const Not<T>& obj) const = 0;
};
/*!
* @brief
* Class for an abstract formula tree with NOT node as root.
*
* Has one Abstract state formula as sub formula/tree.
*
* The subtree is seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractStateFormula
* @see AbstractCslFormula
*/
template <class T>
class Not : public storm::property::abstract::Not<T, AbstractStateFormula<T>>,
public AbstractStateFormula<T> {
public:
/*!
* Empty constructor
*/
Not() {
//intentionally left empty
}
/*!
* Constructor
* @param child The child node
*/
Not(AbstractStateFormula<T>* child) :
storm::property::abstract::Not<T, AbstractStateFormula<T>>(child){
//intentionally left empty
}
/*!
* Destructor
*
* Also deletes the subtree
* (this behavior can be prevented by setting them to NULL before deletion)
*/
virtual ~Not() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new AND-object that is identical the called object.
*/
virtual AbstractStateFormula<T>* clone() const override {
Not<T>* result = new Not<T>();
if (this->childIsSet()) {
result->setChild(this->getChild().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A bit vector indicating all states that satisfy the formula represented by the called object.
*/
virtual storm::storage::BitVector check(const storm::modelchecker::csl::AbstractModelChecker<T>& modelChecker) const override {
return modelChecker.template as<INotModelChecker>()->checkNot(*this);
}
};
} //namespace csl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_CSL_NOT_H_ */

125
src/formula/Csl/Or.h

@ -1,125 +0,0 @@
/*
* Or.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_CSL_OR_H_
#define STORM_FORMULA_CSL_OR_H_
#include "AbstractStateFormula.h"
#include "src/formula/abstract/Or.h"
#include "src/formula/AbstractFormulaChecker.h"
namespace storm {
namespace property {
namespace csl {
template <class T> class Or;
/*!
* @brief Interface class for model checkers that support Or.
*
* All model checkers that support the formula class Or must inherit
* this pure virtual class.
*/
template <class T>
class IOrModelChecker {
public:
/*!
* @brief Evaluates Or formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual storm::storage::BitVector checkOr(const Or<T>& obj) const = 0;
};
/*!
* @brief
* Class for an abstract formula tree with OR node as root.
*
* Has two Abstract state formulas as sub formulas/trees.
*
* As OR is commutative, the order is \e theoretically not important, but will influence the order in which
* the model checker works.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractStateFormula
* @see AbstractCslFormula
*/
template <class T>
class Or : public storm::property::abstract::Or<T, AbstractStateFormula<T>>,
public AbstractStateFormula<T> {
public:
/*!
* Empty constructor.
* Will create an OR-node without subnotes. The result does not represent a complete formula!
*/
Or() {
//intentionally left empty
}
/*!
* Constructor.
* Creates an OR note with the parameters as subtrees.
*
* @param left The left sub formula
* @param right The right sub formula
*/
Or(AbstractStateFormula<T>* left, AbstractStateFormula<T>* right) :
storm::property::abstract::Or<T, AbstractStateFormula<T>>(left, right) {
//intentionally left empty
}
/*!
* Destructor.
*
* The subtrees are deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*/
virtual ~Or() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new AND-object that is identical the called object.
*/
virtual AbstractStateFormula<T>* clone() const override {
Or<T>* result = new Or();
if (this->leftIsSet()) {
result->setLeft(this->getLeft().clone());
}
if (this->rightIsSet()) {
result->setRight(this->getRight().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A bit vector indicating all states that satisfy the formula represented by the called object.
*/
virtual storm::storage::BitVector check(const storm::modelchecker::csl::AbstractModelChecker<T>& modelChecker) const override {
return modelChecker.template as<IOrModelChecker>()->checkOr(*this);
}
};
} //namespace csl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_CSL_OR_H_ */

121
src/formula/Csl/ProbabilisticBoundOperator.h

@ -1,121 +0,0 @@
/*
* ProbabilisticBoundOperator.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_CSL_PROBABILISTICBOUNDOPERATOR_H_
#define STORM_FORMULA_CSL_PROBABILISTICBOUNDOPERATOR_H_
#include "AbstractStateFormula.h"
#include "AbstractPathFormula.h"
#include "src/formula/abstract/ProbabilisticBoundOperator.h"
#include "utility/constants.h"
namespace storm {
namespace property {
namespace csl {
template <class T> class ProbabilisticBoundOperator;
/*!
* @brief Interface class for model checkers that support ProbabilisticBoundOperator.
*
* All model checkers that support the formula class PathBoundOperator must inherit
* this pure virtual class.
*/
template <class T>
class IProbabilisticBoundOperatorModelChecker {
public:
virtual storm::storage::BitVector checkProbabilisticBoundOperator(const ProbabilisticBoundOperator<T>& obj) const = 0;
};
/*!
* @brief
* Class for an abstract formula tree with a P (probablistic) operator node over a probability interval
* as root.
*
* Has one Abstract path formula as sub formula/tree.
*
* @par Semantics
* The formula holds iff the probability that the path formula holds is inside the bounds
* specified in this operator
*
* The subtree is seen as part of the object and deleted with it
* (this behavior can be prevented by setting them to NULL before deletion)
*
*
* @see AbstractStateFormula
* @see AbstractPathFormula
* @see ProbabilisticOperator
* @see ProbabilisticNoBoundsOperator
* @see AbstractCslFormula
*/
template<class T>
class ProbabilisticBoundOperator : public storm::property::abstract::ProbabilisticBoundOperator<T, AbstractPathFormula<T>>,
public AbstractStateFormula<T> {
public:
/*!
* Empty constructor
*/
ProbabilisticBoundOperator() : storm::property::abstract::ProbabilisticBoundOperator<T, AbstractPathFormula<T>>
(LESS_EQUAL, storm::utility::constantZero<T>(), nullptr) {
// Intentionally left empty
}
/*!
* Constructor
*
* @param comparisonRelation The relation to compare the actual value and the bound
* @param bound The bound for the probability
* @param pathFormula The child node
*/
ProbabilisticBoundOperator(
storm::property::ComparisonType comparisonRelation, T bound, AbstractPathFormula<T>* pathFormula)
: storm::property::abstract::ProbabilisticBoundOperator<T, AbstractPathFormula<T>>(comparisonRelation, bound, pathFormula) {
// Intentionally left empty
}
ProbabilisticBoundOperator(
storm::property::ComparisonType comparisonRelation, T bound, AbstractPathFormula<T>* pathFormula, bool minimumOperator)
: storm::property::abstract::ProbabilisticBoundOperator<T, AbstractPathFormula<T>>(comparisonRelation, bound, pathFormula, minimumOperator){
// Intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new AND-object that is identical the called object.
*/
virtual AbstractStateFormula<T>* clone() const override {
ProbabilisticBoundOperator<T>* result = new ProbabilisticBoundOperator<T>();
result->setComparisonOperator(this->getComparisonOperator());
result->setBound(this->getBound());
result->setPathFormula(this->getPathFormula().clone());
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A bit vector indicating all states that satisfy the formula represented by the called object.
*/
virtual storm::storage::BitVector check(const storm::modelchecker::csl::AbstractModelChecker<T>& modelChecker) const override {
return modelChecker.template as<IProbabilisticBoundOperatorModelChecker>()->checkProbabilisticBoundOperator(*this);
}
};
} //namespace csl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_CSL_PROBABILISTICBOUNDOPERATOR_H_ */

115
src/formula/Csl/ProbabilisticNoBoundOperator.h

@ -1,115 +0,0 @@
/*
* ProbabilisticNoBoundOperator.h
*
* Created on: 12.12.2012
* Author: thomas
*/
#ifndef STORM_FORMULA_CSL_PROBABILISTICNOBOUNDOPERATOR_H_
#define STORM_FORMULA_CSL_PROBABILISTICNOBOUNDOPERATOR_H_
#include "AbstractPathFormula.h"
#include "AbstractNoBoundOperator.h"
#include "src/formula/abstract/ProbabilisticNoBoundOperator.h"
namespace storm {
namespace property {
namespace csl {
/*!
* @brief
* Class for an abstract formula tree with a P (probablistic) operator without declaration of probabilities
* as root.
*
* Checking a formula with this operator as root returns the probabilities that the path formula holds
* (for each state)
*
* Has one Abstract path formula as sub formula/tree.
*
* @note
* This class is a hybrid of a state and path formula, and may only appear as the outermost operator.
* Hence, it is seen as neither a state nor a path formula, but is directly derived from AbstractFormula.
*
* @note
* This class does not contain a check() method like the other formula classes.
* The check method should only be called by the model checker to infer the correct check function for sub
* formulas. As this operator can only appear at the root, the method is not useful here.
* Use the checkProbabilisticNoBoundOperator method from the DtmccslModelChecker class instead.
*
* The subtree is seen as part of the object and deleted with it
* (this behavior can be prevented by setting them to NULL before deletion)
*
*
* @see AbstractStateFormula
* @see AbstractPathFormula
* @see ProbabilisticOperator
* @see ProbabilisticIntervalOperator
* @see AbstractCslFormula
*/
template <class T>
class ProbabilisticNoBoundOperator: public storm::property::abstract::ProbabilisticNoBoundOperator<T, AbstractPathFormula<T>>,
public AbstractNoBoundOperator<T> {
public:
/*!
* Empty constructor
*/
ProbabilisticNoBoundOperator() {
// Intentionally left empty
}
/*!
* Constructor
*
* @param pathFormula The child node.
*/
ProbabilisticNoBoundOperator(AbstractPathFormula<T>* pathFormula)
: storm::property::abstract::ProbabilisticNoBoundOperator<T, AbstractPathFormula<T>>(pathFormula) {
// Intentionally left empty
}
/*!
* Constructor
*
* @param pathFormula The child node.
*/
ProbabilisticNoBoundOperator(AbstractPathFormula<T>* pathFormula, bool minimumOperator)
: storm::property::abstract::ProbabilisticNoBoundOperator<T, AbstractPathFormula<T>>(pathFormula, minimumOperator) {
// Intentionally left empty
}
/*!
* Destructor
*/
virtual ~ProbabilisticNoBoundOperator() {
// Intentionally left empty
}
virtual AbstractNoBoundOperator<T>* clone() const override {
ProbabilisticNoBoundOperator<T>* result = new ProbabilisticNoBoundOperator<T>();
if (this->pathFormulaIsSet()) {
result->setPathFormula(this->getPathFormula().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @note This function is not implemented in this class.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::csl::AbstractModelChecker<T>& modelChecker, bool qualitative=false) const override {
return this->getPathFormula().check(modelChecker, qualitative);
}
};
} //namespace csl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_CSL_PROBABILISTICNOBOUNDOPERATOR_H_ */

118
src/formula/Csl/SteadyStateBoundOperator.h

@ -1,118 +0,0 @@
/*
* SteadyState.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_CSL_STEADYSTATEOPERATOR_H_
#define STORM_FORMULA_CSL_STEADYSTATEOPERATOR_H_
#include "AbstractStateFormula.h"
#include "src/formula/abstract/SteadyStateBoundOperator.h"
#include "src/formula/AbstractFormulaChecker.h"
namespace storm {
namespace property {
namespace csl {
template <class T> class SteadyStateBoundOperator;
/*!
* @brief Interface class for model checkers that support SteadyStateOperator.
*
* All model checkers that support the formula class SteadyStateOperator must inherit
* this pure virtual class.
*/
template <class T>
class ISteadyStateBoundOperatorModelChecker {
public:
/*!
* @brief Evaluates SteadyStateOperator formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual storm::storage::BitVector checkSteadyStateBoundOperator(const SteadyStateBoundOperator<T>& obj) const = 0;
};
/*!
* @brief
* Class for an Abstract (path) formula tree with a SteadyStateOperator node as root.
*
* Has two Abstract state formulas as sub formulas/trees.
*
* @par Semantics
* The formula holds iff \e child holds SteadyStateOperator step, \e child holds
*
* The subtree is seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractPathFormula
* @see AbstractCslFormula
*/
template <class T>
class SteadyStateBoundOperator : public storm::property::abstract::SteadyStateBoundOperator<T, AbstractStateFormula<T>>,
public AbstractStateFormula<T> {
public:
/*!
* Empty constructor
*/
SteadyStateBoundOperator() : storm::property::abstract::SteadyStateBoundOperator<T, AbstractStateFormula<T>>
(LESS_EQUAL, storm::utility::constantZero<T>(), nullptr) {
// Intentionally left empty
}
/*!
* Constructor
*
* @param stateFormula The child node
*/
SteadyStateBoundOperator(
storm::property::ComparisonType comparisonRelation, T bound, AbstractStateFormula<T>* stateFormula) :
storm::property::abstract::SteadyStateBoundOperator<T, AbstractStateFormula<T>>(comparisonRelation, bound, stateFormula) {
}
/*!
* Destructor
*/
virtual ~SteadyStateBoundOperator() {
// Intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new BoundedUntil-object that is identical the called object.
*/
virtual AbstractStateFormula<T>* clone() const override {
SteadyStateBoundOperator<T>* result = new SteadyStateBoundOperator<T>();
result->setStateFormula(this->getStateFormula().clone());
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual storm::storage::BitVector check(const storm::modelchecker::csl::AbstractModelChecker<T>& modelChecker) const override {
return modelChecker.template as<ISteadyStateBoundOperatorModelChecker>()->checkSteadyStateBoundOperator(*this);
}
};
} //namespace csl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_CSL_STEADYSTATEOPERATOR_H_ */

100
src/formula/Csl/SteadyStateNoBoundOperator.h

@ -1,100 +0,0 @@
/*
* SteadyStateNoBoundOperator.h
*
* Created on: 09.04.2013
* Author: thomas
*/
#ifndef STORM_FORMULA_CSL_STEADYSTATENOBOUNDOPERATOR_H_
#define STORM_FORMULA_CSL_STEADYSTATENOBOUNDOPERATOR_H_
#include "AbstractStateFormula.h"
#include "AbstractNoBoundOperator.h"
#include "src/formula/abstract/SteadyStateNoBoundOperator.h"
namespace storm {
namespace property {
namespace csl {
template <class T> class SteadyStateNoBoundOperator;
/*!
* @brief Interface class for model checkers that support SteadyStateOperator.
*
* All model checkers that support the formula class SteadyStateOperator must inherit
* this pure virtual class.
*/
template <class T>
class ISteadyStateNoBoundOperatorModelChecker {
public:
/*!
* @brief Evaluates SteadyStateOperator formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkSteadyStateNoBoundOperator(const SteadyStateNoBoundOperator<T>& obj) const = 0;
};
template <class T>
class SteadyStateNoBoundOperator: public storm::property::abstract::SteadyStateNoBoundOperator<T, AbstractStateFormula<T>>,
public AbstractNoBoundOperator<T> {
public:
/*!
* Empty constructor
*/
SteadyStateNoBoundOperator() : storm::property::abstract::SteadyStateNoBoundOperator<T, AbstractStateFormula<T>>() {
// Intentionally left empty
}
/*!
* Constructor
*
* @param stateFormula The state formula that forms the subtree
*/
SteadyStateNoBoundOperator(AbstractStateFormula<T>* stateFormula)
: storm::property::abstract::SteadyStateNoBoundOperator<T, AbstractStateFormula<T>>(stateFormula) {
// Intentionally left empty
}
/*!
* Destructor
*/
~SteadyStateNoBoundOperator() {
// Intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new BoundedUntil-object that is identical the called object.
*/
virtual AbstractNoBoundOperator <T>* clone() const override {
SteadyStateNoBoundOperator<T>* result = new SteadyStateNoBoundOperator<T>();
result->setStateFormula(this->getStateFormula().clone());
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::csl::AbstractModelChecker<T>& modelChecker, bool qualitative=false) const override {
return modelChecker.template as<ISteadyStateNoBoundOperatorModelChecker>()->checkSteadyStateNoBoundOperator(*this);
}
};
} /* namespace csl */
} /* namespace property */
} /* namespace storm */
#endif /* STORM_FORMULA_CSL_STEADYSTATENOBOUNDOPERATOR_H_ */

97
src/formula/Csl/TimeBoundedEventually.h

@ -1,97 +0,0 @@
/*
* TimeBoundedEventually.h
*
* Created on: 10.04.2013
* Author: thomas
*/
#ifndef STORM_FORMULA_CSL_TIMEBOUNDEDEVENTUALLY_H_
#define STORM_FORMULA_CSL_TIMEBOUNDEDEVENTUALLY_H_
#include "src/formula/abstract/TimeBoundedEventually.h"
#include "AbstractPathFormula.h"
#include "AbstractStateFormula.h"
namespace storm {
namespace property {
namespace csl {
template<class T> class TimeBoundedEventually;
/*!
* @brief Interface class for model checkers that support TimeBoundedEventually.
*
* All model checkers that support the formula class BoundedEventually must inherit
* this pure virtual class.
*/
template <class T>
class ITimeBoundedEventuallyModelChecker {
public:
/*!
* @brief Evaluates TimeBoundedUntil formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkTimeBoundedEventually(const TimeBoundedEventually<T>& obj, bool qualitative) const = 0;
};
template<class T>
class TimeBoundedEventually: public storm::property::abstract::TimeBoundedEventually<T, AbstractStateFormula<T>>,
public AbstractPathFormula<T> {
public:
/**
* Simple constructor: Only sets the bounds
*
* @param lowerBound
* @param upperBound
*/
TimeBoundedEventually(T lowerBound, T upperBound)
: storm::property::abstract::TimeBoundedEventually<T, AbstractStateFormula<T>>(lowerBound, upperBound) {
// Intentionally left empty
}
TimeBoundedEventually(T lowerBound, T upperBound, AbstractStateFormula<T>* child)
: storm::property::abstract::TimeBoundedEventually<T, AbstractStateFormula<T>>(lowerBound, upperBound, child) {
// Intentionally left empty
}
virtual ~TimeBoundedEventually() {
// Intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new BoundedUntil-object that is identical the called object.
*/
virtual AbstractPathFormula<T>* clone() const override {
TimeBoundedEventually<T>* result = new TimeBoundedEventually<T>(this->getLowerBound(), this->getUpperBound());
if (this->childIsSet()) {
result->setChild(this->getChild().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::csl::AbstractModelChecker<T>& modelChecker, bool qualitative) const override {
return modelChecker.template as<ITimeBoundedEventuallyModelChecker>()->checkTimeBoundedEventually(*this, qualitative);
}
};
} /* namespace csl */
} /* namespace property */
} /* namespace storm */
#endif /* STORM_FORMULA_CSL_TIMEBOUNDEDEVENTUALLY_H_ */

111
src/formula/Csl/TimeBoundedUntil.h

@ -1,111 +0,0 @@
/*
* TimeBoundedUntil.h
*
* Created on: 10.04.2013
* Author: thomas
*/
#ifndef STORM_FORMULA_CSL_TIMEBOUNDEDUNTIL_H_
#define STORM_FORMULA_CSL_TIMEBOUNDEDUNTIL_H_
#include "AbstractPathFormula.h"
#include "AbstractStateFormula.h"
#include "src/formula/abstract/TimeBoundedUntil.h"
namespace storm {
namespace property {
namespace csl {
template <class T> class TimeBoundedUntil;
/*!
* @brief Interface class for model checkers that support TimeBoundedUntil.
*
* All model checkers that support the formula class BoundedEventually must inherit
* this pure virtual class.
*/
template <class T>
class ITimeBoundedUntilModelChecker {
public:
/*!
* @brief Evaluates TimeBoundedUntil formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkTimeBoundedUntil(const TimeBoundedUntil<T>& obj, bool qualitative) const = 0;
};
template <class T>
class TimeBoundedUntil: public storm::property::abstract::TimeBoundedUntil<T, AbstractStateFormula<T>>,
public AbstractPathFormula<T> {
public:
/**
* Constructor providing bounds only;
* Sub formulas are set to null.
*
* @param lowerBound
* @param upperBound
*/
TimeBoundedUntil(T lowerBound, T upperBound) :
storm::property::abstract::TimeBoundedUntil<T, AbstractStateFormula<T>>(lowerBound, upperBound) {
// Intentionally left empty
}
/**
* Full constructor
* @param lowerBound
* @param upperBound
* @param left
* @param right
*/
TimeBoundedUntil(T lowerBound, T upperBound, AbstractStateFormula<T>* left, AbstractStateFormula<T>* right) :
storm::property::abstract::TimeBoundedUntil<T, AbstractStateFormula<T>>(lowerBound, upperBound, left, right) {
}
/*!
* Destructor
*/
virtual ~TimeBoundedUntil() {
// Intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new BoundedUntil-object that is identical the called object.
*/
virtual AbstractPathFormula<T>* clone() const override {
TimeBoundedUntil<T>* result = new TimeBoundedUntil<T>(this->getLowerBound(), this->getUpperBound());
if (this->leftIsSet()) {
result->setLeft(this->getLeft().clone());
}
if (this->rightIsSet()) {
result->setRight(this->getRight().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::csl::AbstractModelChecker<T>& modelChecker, bool qualitative) const override {
return modelChecker.template as<ITimeBoundedUntilModelChecker>()->checkTimeBoundedUntil(*this, qualitative);
}
};
} /* namespace csl */
} /* namespace property */
} /* namespace storm */
#endif /* STORM_FORMULA_CSL_TIMEBOUNDEDUNTIL_H_ */

125
src/formula/Csl/Until.h

@ -1,125 +0,0 @@
/*
* Until.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_CSL_UNTIL_H_
#define STORM_FORMULA_CSL_UNTIL_H_
#include "AbstractPathFormula.h"
#include "AbstractStateFormula.h"
#include "src/formula/abstract/Until.h"
#include "src/formula/AbstractFormulaChecker.h"
namespace storm {
namespace property {
namespace csl {
template <class T> class Until;
/*!
* @brief Interface class for model checkers that support Until.
*
* All model checkers that support the formula class Until must inherit
* this pure virtual class.
*/
template <class T>
class IUntilModelChecker {
public:
/*!
* @brief Evaluates Until formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkUntil(const Until<T>& obj, bool qualitative) const = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with an Until node as root.
*
* Has two Abstract state formulas as sub formulas/trees.
*
* @par Semantics
* The formula holds iff eventually, formula \e right (the right subtree) holds, and before,
* \e left holds always.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractPathFormula
* @see AbstractCslFormula
*/
template <class T>
class Until : public storm::property::abstract::Until<T, AbstractStateFormula<T>>,
public AbstractPathFormula<T> {
public:
/*!
* Empty constructor
*/
Until() {
// Intentionally left empty
}
/*!
* Constructor
*
* @param left The left formula subtree
* @param right The left formula subtree
*/
Until(AbstractStateFormula<T>* left, AbstractStateFormula<T>* right)
: storm::property::abstract::Until<T, AbstractStateFormula<T>>(left, right) {
// Intentionally left empty
}
/*!
* Destructor.
*
* Also deletes the subtrees.
* (this behaviour can be prevented by setting the subtrees to NULL before deletion)
*/
virtual ~Until() {
// Intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new BoundedUntil-object that is identical the called object.
*/
virtual AbstractPathFormula<T>* clone() const override {
Until<T>* result = new Until();
if (this->leftIsSet()) {
result->setLeft(this->getLeft().clone());
}
if (this->rightIsSet()) {
result->setRight(this->getRight().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::csl::AbstractModelChecker<T>& modelChecker, bool qualitative) const override {
return modelChecker.template as<IUntilModelChecker>()->checkUntil(*this, qualitative);
}
};
} //namespace csl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_CSL_UNTIL_H_ */

150
src/formula/Ltl/And.h

@ -1,150 +0,0 @@
/*
* And.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_LTL_AND_H_
#define STORM_FORMULA_LTL_AND_H_
#include "AbstractLtlFormula.h"
#include "src/formula/abstract/And.h"
#include "src/formula/AbstractFormulaChecker.h"
#include "src/modelchecker/ltl/ForwardDeclarations.h"
#include <string>
namespace storm {
namespace property {
namespace ltl {
template <class T> class And;
/*!
* @brief Interface class for model checkers that support And.
*
* All model checkers that support the formula class And must inherit
* this pure virtual class.
*/
template <class T>
class IAndModelChecker {
public:
/*!
* @brief Evaluates And formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkAnd(const And<T>& obj) const = 0;
};
/*!
* @brief Interface class for visitors that support And.
*
* All visitors that support the formula class And must inherit
* this pure virtual class.
*/
template <class T>
class IAndVisitor {
public:
/*!
* @brief Evaluates And formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual void visitAnd(const And<T>& obj) = 0;
};
/*!
* @brief
* Class for an abstract formula tree with AND node as root.
*
* Has two Abstract LTL formulas as sub formulas/trees.
*
* As AND is commutative, the order is \e theoretically not important, but will influence the order in which
* the model checker works.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractLtlFormula
*/
template <class T>
class And : public storm::property::abstract::And<T, AbstractLtlFormula<T>>, public AbstractLtlFormula<T> {
public:
/*!
* Empty constructor.
* Will create an AND-node without subnotes. Will not represent a complete formula!
*/
And() {
//intentionally left empty
}
/*!
* Constructor.
* Creates an AND node with the parameters as subtrees.
*
* @param left The left sub formula
* @param right The right sub formula
*/
And(AbstractLtlFormula<T>* left, AbstractLtlFormula<T>* right)
: storm::property::abstract::And<T, AbstractLtlFormula<T>>(left, right) {
//intentionally left empty
}
/*!
* Destructor.
*
* The subtrees are deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*/
virtual ~And() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new AND-object that is identical the called object.
*/
virtual AbstractLtlFormula<T>* clone() const override {
And<T>* result = new And();
if (this->leftIsSet()) {
result->setLeft(this->getLeft().clone());
}
if (this->rightIsSet()) {
result->setRight(this->getRight().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A bit vector indicating all states that satisfy the formula represented by the called object.
*/
virtual std::vector<T> check(const storm::modelchecker::ltl::AbstractModelChecker<T>& modelChecker) const override {
return modelChecker.template as<IAndModelChecker>()->checkAnd(*this);
}
virtual void visit(visitor::AbstractLtlFormulaVisitor<T>& visitor) const override {
visitor.template as<IAndVisitor>()->visitAnd(*this);
}
};
} //namespace ltl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_LTL_AND_H_ */

129
src/formula/Ltl/Ap.h

@ -1,129 +0,0 @@
/*
* Ap.h
*
* Created on: 22.04.2013
* Author: thomas
*/
#ifndef STORM_FORMULA_LTL_AP_H_
#define STORM_FORMULA_LTL_AP_H_
#include "AbstractLtlFormula.h"
#include "src/formula/abstract/Ap.h"
namespace storm {
namespace property {
namespace ltl {
template <class T> class Ap;
/*!
* @brief Interface class for model checkers that support And.
*
* All model checkers that support the formula class And must inherit
* this pure virtual class.
*/
template <class T>
class IApModelChecker {
public:
/*!
* @brief Evaluates And formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkAp(const Ap<T>& obj) const = 0;
};
/*!
* @brief Interface class for visitors that support Ap.
*
* All visitors that support the formula class Ap must inherit
* this pure virtual class.
*/
template <class T>
class IApVisitor {
public:
/*!
* @brief Evaluates And formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual void visitAp(const Ap<T>& obj) = 0;
};
/*!
* @brief
* Class for an abstract formula tree with atomic proposition as root.
*
* This class represents the leaves in the formula tree.
*
* @see AbstractLtlFormula
*/
template <class T>
class Ap: public storm::property::abstract::Ap<T>,
public storm::property::ltl::AbstractLtlFormula<T> {
public:
/*!
* Empty constructor
*/
Ap() {
// Intentionally left empty
}
/*!
* Constructor
*
* Creates a new atomic proposition leaf, with the label Ap
*
* @param ap The string representing the atomic proposition
*/
Ap(std::string ap) :
storm::property::abstract::Ap<T>(ap) {
// Intentionally left empty
}
/*!
* Destructor
*/
virtual ~Ap() {
// Intentionally left empty
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @note This function is not implemented in this class.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::ltl::AbstractModelChecker<T>& modelChecker) const override {
return modelChecker.template as<IApModelChecker>()->checkAp(*this);
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new AND-object that is identical the called object.
*/
virtual AbstractLtlFormula<T>* clone() const override {
return new Ap(this->getAp());
}
virtual void visit(visitor::AbstractLtlFormulaVisitor<T>& visitor) const override {
visitor.template as<IApVisitor>()->visitAp(*this);
}
};
} /* namespace ltl */
} /* namespace property */
} /* namespace storm */
#endif /* STORM_FORMULA_LTL_AP_H_ */

146
src/formula/Ltl/BoundedEventually.h

@ -1,146 +0,0 @@
/*
* BoundedUntil.h
*
* Created on: 27.11.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_LTL_BOUNDEDEVENTUALLY_H_
#define STORM_FORMULA_LTL_BOUNDEDEVENTUALLY_H_
#include "src/formula/abstract/BoundedEventually.h"
#include "AbstractLtlFormula.h"
#include "src/formula/AbstractFormulaChecker.h"
#include <cstdint>
#include <string>
#include "src/modelchecker/ltl/ForwardDeclarations.h"
namespace storm {
namespace property {
namespace ltl {
template <class T> class BoundedEventually;
/*!
* @brief Interface class for model checkers that support BoundedEventually.
*
* All model checkers that support the formula class BoundedEventually must inherit
* this pure virtual class.
*/
template <class T>
class IBoundedEventuallyModelChecker {
public:
/*!
* @brief Evaluates BoundedEventually formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkBoundedEventually(const BoundedEventually<T>& obj) const = 0;
};
/*!
* @brief Interface class for visitors that support BoundedEventually.
*
* All visitors that support the formula class BoundedEventually must inherit
* this pure virtual class.
*/
template <class T>
class IBoundedEventuallyVisitor {
public:
/*!
* @brief Evaluates BoundedEventually formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual void visitBoundedEventually(const BoundedEventually<T>& obj) = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with a BoundedEventually node as root.
*
* Has one Abstract LTL formulas as sub formula/tree.
*
* @par Semantics
* The formula holds iff in at most \e bound steps, formula \e child holds.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractLtlFormula
*/
template <class T>
class BoundedEventually : public storm::property::abstract::BoundedEventually<T, AbstractLtlFormula<T>>,
public AbstractLtlFormula<T> {
public:
/*!
* Empty constructor
*/
BoundedEventually() {
//intentionally left empty
}
/*!
* Constructor
*
* @param child The child formula subtree
* @param bound The maximal number of steps
*/
BoundedEventually(AbstractLtlFormula<T>* child, uint_fast64_t bound) :
storm::property::abstract::BoundedEventually<T, AbstractLtlFormula<T>>(child, bound){
//intentionally left empty
}
/*!
* Destructor.
*
* Also deletes the subtrees.
* (this behaviour can be prevented by setting the subtrees to NULL before deletion)
*/
virtual ~BoundedEventually() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new BoundedUntil-object that is identical the called object.
*/
virtual AbstractLtlFormula<T>* clone() const override {
BoundedEventually<T>* result = new BoundedEventually<T>();
result->setBound(this->getBound());
if (this->childIsSet()) {
result->setChild(this->getChild().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::ltl::AbstractModelChecker<T>& modelChecker) const override {
return modelChecker.template as<IBoundedEventuallyModelChecker>()->checkBoundedEventually(*this);
}
virtual void visit(visitor::AbstractLtlFormulaVisitor<T>& visitor) const override {
visitor.template as<IBoundedEventuallyVisitor>()->visitBoundedEventually(*this);
}
};
} //namespace ltl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_LTL_BOUNDEDUNTIL_H_ */

163
src/formula/Ltl/BoundedUntil.h

@ -1,163 +0,0 @@
/*
* BoundedUntil.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_LTL_BOUNDEDUNTIL_H_
#define STORM_FORMULA_LTL_BOUNDEDUNTIL_H_
#include "src/formula/abstract/BoundedUntil.h"
#include "AbstractLtlFormula.h"
#include <cstdint>
#include <string>
#include "src/modelchecker/ltl/ForwardDeclarations.h"
namespace storm {
namespace property {
namespace ltl {
template <class T> class BoundedUntil;
/*!
* @brief Interface class for model checkers that support BoundedUntil.
*
* All model checkers that support the formula class BoundedUntil must inherit
* this pure virtual class.
*/
template <class T>
class IBoundedUntilModelChecker {
public:
/*!
* @brief Evaluates BoundedUntil formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkBoundedUntil(const BoundedUntil<T>& obj) const = 0;
};
/*!
* @brief Interface class for visitors that support BoundedUntil.
*
* All visitors that support the formula class BoundedUnitl must inherit
* this pure virtual class.
*/
template <class T>
class IBoundedUntilVisitor {
public:
/*!
* @brief Visits BoundedUntil formula.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual void visitBoundedUntil(const BoundedUntil<T>& obj) = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with a BoundedUntil node as root.
*
* Has two Abstract LTL formulas as sub formulas/trees.
*
* @par Semantics
* The formula holds iff in at most \e bound steps, formula \e right (the right subtree) holds, and before,
* \e left holds.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractLtlFormula
*/
template <class T>
class BoundedUntil : public storm::property::abstract::BoundedUntil<T, AbstractLtlFormula<T>>,
public AbstractLtlFormula<T> {
public:
/*!
* Empty constructor
*/
BoundedUntil() {
//Intentionally left empty
}
/*!
* Constructor
*
* @param left The left formula subtree
* @param right The left formula subtree
* @param bound The maximal number of steps
*/
BoundedUntil(AbstractLtlFormula<T>* left, AbstractLtlFormula<T>* right,
uint_fast64_t bound) :
storm::property::abstract::BoundedUntil<T, AbstractLtlFormula<T>>(left,right,bound) {
//intentionally left empty
}
/*!
* Destructor.
*
* Also deletes the subtrees.
* (this behaviour can be prevented by setting the subtrees to NULL before deletion)
*/
virtual ~BoundedUntil() {
//intentionally left empty
}
/*!
* @brief Return string representation of this formula.
*
* In LTL, brackets are needed around the until, as Until may appear nested (in other logics, Until always is the
* root of a path formula); hence this function is overwritten in this class.
*
* @return A string representation of the formula.
*/
virtual std::string toString() const {
return "(" + storm::property::abstract::BoundedUntil<T, AbstractLtlFormula<T>>::toString() + ")";
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new BoundedUntil-object that is identical the called object.
*/
virtual AbstractLtlFormula<T>* clone() const override {
BoundedUntil<T>* result = new BoundedUntil<T>();
result->setBound(this->getBound());
if (this->leftIsSet()) {
result->setLeft(this->getLeft().clone());
}
if (this->rightIsSet()) {
result->setRight(this->getRight().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::ltl::AbstractModelChecker<T>& modelChecker) const {
return modelChecker.template as<IBoundedUntilModelChecker>()->checkBoundedUntil(*this);
}
virtual void visit(visitor::AbstractLtlFormulaVisitor<T>& visitor) const override {
visitor.template as<IBoundedUntilVisitor>()->visitBoundedUntil(*this);
}
};
} //namespace ltl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_LTL_BOUNDEDUNTIL_H_ */

140
src/formula/Ltl/Eventually.h

@ -1,140 +0,0 @@
/*
* Next.h
*
* Created on: 26.12.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_LTL_EVENTUALLY_H_
#define STORM_FORMULA_LTL_EVENTUALLY_H_
#include "src/formula/abstract/Eventually.h"
#include "AbstractLtlFormula.h"
#include "src/modelchecker/ltl/ForwardDeclarations.h"
namespace storm {
namespace property {
namespace ltl {
template <class T> class Eventually;
/*!
* @brief Interface class for model checkers that support Eventually.
*
* All model checkers that support the formula class Eventually must inherit
* this pure virtual class.
*/
template <class T>
class IEventuallyModelChecker {
public:
/*!
* @brief Evaluates Eventually formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkEventually(const Eventually<T>& obj) const = 0;
};
/*!
* @brief Interface class for visitors that support Eventually.
*
* All visitors that support the formula class Eventually must inherit
* this pure virtual class.
*/
template <class T>
class IEventuallyVisitor {
public:
/*!
* @brief Visits Eventually formula.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual void visitEventually(const Eventually<T>& obj) = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with an Eventually node as root.
*
* Has one Abstract LTL formula as sub formula/tree.
*
* @par Semantics
* The formula holds iff eventually \e child holds.
*
* The subtree is seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to nullptr before deletion)
*
* @see AbstractLtlFormula
*/
template <class T>
class Eventually : public storm::property::abstract::Eventually<T, AbstractLtlFormula<T>>,
public AbstractLtlFormula<T> {
public:
/*!
* Empty constructor
*/
Eventually() {
// Intentionally left empty
}
/*!
* Constructor
*
* @param child The child node
*/
Eventually(AbstractLtlFormula<T>* child)
: storm::property::abstract::Eventually<T, AbstractLtlFormula<T>>(child) {
}
/*!
* Constructor.
*
* Also deletes the subtree.
* (this behaviour can be prevented by setting the subtrees to nullptr before deletion)
*/
virtual ~Eventually() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new Eventually-object that is identical the called object.
*/
virtual AbstractLtlFormula<T>* clone() const override {
Eventually<T>* result = new Eventually<T>();
if (this->childIsSet()) {
result->setChild(this->getChild().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::ltl::AbstractModelChecker<T>& modelChecker) const {
return modelChecker.template as<IEventuallyModelChecker>()->checkEventually(*this);
}
virtual void visit(visitor::AbstractLtlFormulaVisitor<T>& visitor) const override {
visitor.template as<IEventuallyVisitor>()->visitEventually(*this);
}
};
} //namespace ltl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_LTL_EVENTUALLY_H_ */

142
src/formula/Ltl/Globally.h

@ -1,142 +0,0 @@
/*
* Next.h
*
* Created on: 26.12.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_LTL_GLOBALLY_H_
#define STORM_FORMULA_LTL_GLOBALLY_H_
#include "src/formula/abstract/Globally.h"
#include "AbstractLtlFormula.h"
#include "src/formula/AbstractFormulaChecker.h"
#include "src/modelchecker/ltl/ForwardDeclarations.h"
namespace storm {
namespace property {
namespace ltl {
template <class T> class Globally;
/*!
* @brief Interface class for model checkers that support Globally.
*
* All model checkers that support the formula class Globally must inherit
* this pure virtual class.
*/
template <class T>
class IGloballyModelChecker {
public:
/*!
* @brief Evaluates Globally formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkGlobally(const Globally<T>& obj) const = 0;
};
/*!
* @brief Interface class for visitors that support Globally.
*
* All visitors that support the formula class Globally must inherit
* this pure virtual class.
*/
template <class T>
class IGloballyVisitor {
public:
/*!
* @brief Visits Globally formula.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual void visitGlobally(const Globally<T>& obj) = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with a Globally node as root.
*
* Has one Abstract LTL formula as sub formula/tree.
*
* @par Semantics
* The formula holds iff globally \e child holds.
*
* The subtree is seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to nullptr before deletion)
*
* @see AbstractLtlFormula
*/
template <class T>
class Globally : public storm::property::abstract::Globally<T, AbstractLtlFormula<T>>,
public AbstractLtlFormula<T> {
public:
/*!
* Empty constructor
*/
Globally() {
//intentionally left empty
}
/*!
* Constructor
*
* @param child The child node
*/
Globally(AbstractLtlFormula<T>* child)
: storm::property::abstract::Globally<T, AbstractLtlFormula<T>>(child) {
//intentionally left empty
}
/*!
* Constructor.
*
* Also deletes the subtree.
* (this behaviour can be prevented by setting the subtrees to nullptr before deletion)
*/
virtual ~Globally() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new Globally-object that is identical the called object.
*/
virtual AbstractLtlFormula<T>* clone() const override {
Globally<T>* result = new Globally<T>();
if (this->childIsSet()) {
result->setChild(this->getChild().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::ltl::AbstractModelChecker<T>& modelChecker) const {
return modelChecker.template as<IGloballyModelChecker>()->checkGlobally(*this);
}
virtual void visit(visitor::AbstractLtlFormulaVisitor<T>& visitor) const override {
visitor.template as<IGloballyVisitor>()->visitGlobally(*this);
}
};
} //namespace ltl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_LTL_GLOBALLY_H_ */

140
src/formula/Ltl/Next.h

@ -1,140 +0,0 @@
/*
* Next.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_LTL_NEXT_H_
#define STORM_FORMULA_LTL_NEXT_H_
#include "AbstractLtlFormula.h"
#include "src/formula/abstract/Next.h"
#include "src/formula/AbstractFormulaChecker.h"
namespace storm {
namespace property {
namespace ltl {
template <class T> class Next;
/*!
* @brief Interface class for model checkers that support Next.
*
* All model checkers that support the formula class Next must inherit
* this pure virtual class.
*/
template <class T>
class INextModelChecker {
public:
/*!
* @brief Evaluates Next formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkNext(const Next<T>& obj) const = 0;
};
/*!
* @brief Interface class for visitors that support Next.
*
* All visitors that support the formula class Next must inherit
* this pure virtual class.
*/
template <class T>
class INextVisitor {
public:
/*!
* @brief Visits Next formula.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual void visitNext(const Next<T>& obj) = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with a Next node as root.
*
* Has two Abstract LTL formulas as sub formulas/trees.
*
* @par Semantics
* The formula holds iff in the next step, \e child holds
*
* The subtree is seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractLtlFormula
*/
template <class T>
class Next : public storm::property::abstract::Next<T, AbstractLtlFormula<T>>,
public AbstractLtlFormula<T> {
public:
/*!
* Empty constructor
*/
Next() {
//intentionally left empty
}
/*!
* Constructor
*
* @param child The child node
*/
Next(AbstractLtlFormula<T>* child)
: storm::property::abstract::Next<T, AbstractLtlFormula<T>>(child) {
//intentionally left empty
}
/*!
* Constructor.
*
* Also deletes the subtree.
* (this behaviour can be prevented by setting the subtrees to NULL before deletion)
*/
virtual ~Next() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new BoundedUntil-object that is identical the called object.
*/
virtual AbstractLtlFormula<T>* clone() const override {
Next<T>* result = new Next<T>();
if (this->childIsSet()) {
result->setChild(this->getChild().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::ltl::AbstractModelChecker<T>& modelChecker) const {
return modelChecker.template as<INextModelChecker>()->checkNext(*this);
}
virtual void visit(visitor::AbstractLtlFormulaVisitor<T>& visitor) const override {
visitor.template as<INextVisitor>()->visitNext(*this);
}
};
} //namespace ltl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_LTL_NEXT_H_ */

136
src/formula/Ltl/Not.h

@ -1,136 +0,0 @@
/*
* Not.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_LTL_NOT_H_
#define STORM_FORMULA_LTL_NOT_H_
#include "AbstractLtlFormula.h"
#include "src/formula/abstract/Not.h"
#include "src/formula/AbstractFormulaChecker.h"
namespace storm {
namespace property {
namespace ltl {
template <class T> class Not;
/*!
* @brief Interface class for model checkers that support Not.
*
* All model checkers that support the formula class Not must inherit
* this pure virtual class.
*/
template <class T>
class INotModelChecker {
public:
/*!
* @brief Evaluates Not formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkNot(const Not<T>& obj) const = 0;
};
/*!
* @brief Interface class for visitors that support Not.
*
* All visitors that support the formula class Not must inherit
* this pure virtual class.
*/
template <class T>
class INotVisitor {
public:
/*!
* @brief Visits Not formula.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual void visitNot(const Not<T>& obj) = 0;
};
/*!
* @brief
* Class for an abstract formula tree with NOT node as root.
*
* Has one Abstract LTL formula as sub formula/tree.
*
* The subtree is seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractLtlFormula
*/
template <class T>
class Not : public storm::property::abstract::Not<T, AbstractLtlFormula<T>>,
public AbstractLtlFormula<T> {
public:
/*!
* Empty constructor
*/
Not() {
//intentionally left empty
}
/*!
* Constructor
* @param child The child node
*/
Not(AbstractLtlFormula<T>* child) :
storm::property::abstract::Not<T, AbstractLtlFormula<T>>(child){
//intentionally left empty
}
/*!
* Destructor
*
* Also deletes the subtree
* (this behavior can be prevented by setting them to NULL before deletion)
*/
virtual ~Not() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new AND-object that is identical the called object.
*/
virtual AbstractLtlFormula<T>* clone() const override {
Not<T>* result = new Not<T>();
if (this->childIsSet()) {
result->setChild(this->getChild().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A bit vector indicating all states that satisfy the formula represented by the called object.
*/
virtual std::vector<T> check(const storm::modelchecker::ltl::AbstractModelChecker<T>& modelChecker) const override {
return modelChecker.template as<INotModelChecker>()->checkNot(*this);
}
virtual void visit(visitor::AbstractLtlFormulaVisitor<T>& visitor) const override {
visitor.template as<INotVisitor>()->visitNot(*this);
}
};
} //namespace ltl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_LTL_NOT_H_ */

141
src/formula/Ltl/Or.h

@ -1,141 +0,0 @@
/*
* Or.h
*
* Created on: 22.04.2013
* Author: thomas
*/
#ifndef STORM_FORMULA_LTL_OR_H_
#define STORM_FORMULA_LTL_OR_H_
#include "AbstractLtlFormula.h"
#include "src/formula/abstract/Or.h"
namespace storm {
namespace property {
namespace ltl {
template <class T> class Or;
/*!
* @brief Interface class for model checkers that support And.
*
* All model checkers that support the formula class And must inherit
* this pure virtual class.
*/
template <class T>
class IOrModelChecker {
public:
/*!
* @brief Evaluates And formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkOr(const Or<T>& obj) const = 0;
};
/*!
* @brief Interface class for visitors that support Or.
*
* All visitors that support the formula class Or must inherit
* this pure virtual class.
*/
template <class T>
class IOrVisitor {
public:
/*!
* @brief Visits Or formula.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual void visitOr(const Or<T>& obj) = 0;
};
/*!
* @brief
* Class for an abstract formula tree with OR node as root.
*
* Has two LTL formulas as sub formulas/trees.
*
* As OR is commutative, the order is \e theoretically not important, but will influence the order in which
* the model checker works.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractLtlFormula
*/
template <class T>
class Or: public storm::property::abstract::Or<T, AbstractLtlFormula<T>>,
public storm::property::ltl::AbstractLtlFormula<T> {
public:
/*!
* Empty constructor
*/
Or() {
// Intentionally left empty
}
/*!
* Constructor
* Creates an OR node with the parameters as subtrees.
*
* @param left The left subformula
* @param right The right subformula
*/
Or(AbstractLtlFormula<T>* left, AbstractLtlFormula<T>* right)
: storm::property::abstract::Or<T,AbstractLtlFormula<T>>(left, right) {
// Intentionally left empty
}
/*!
* Destructor
*/
virtual ~Or() {
// Intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new AND-object that is identical the called object.
*/
virtual AbstractLtlFormula<T>* clone() const override {
Or<T>* result = new Or();
if (this->leftIsSet()) {
result->setLeft(this->getLeft().clone());
}
if (this->rightIsSet()) {
result->setRight(this->getRight().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A bit vector indicating all states that satisfy the formula represented by the called object.
*/
virtual std::vector<T> check(const storm::modelchecker::ltl::AbstractModelChecker<T>& modelChecker) const override {
return modelChecker.template as<IOrModelChecker>()->checkOr(*this);
}
virtual void visit(visitor::AbstractLtlFormulaVisitor<T>& visitor) const override {
visitor.template as<IOrVisitor>()->visitOr(*this);
}
};
} /* namespace ltl */
} /* namespace property */
} /* namespace storm */
#endif /* OR_H_ */

157
src/formula/Ltl/Until.h

@ -1,157 +0,0 @@
/*
* Until.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_LTL_UNTIL_H_
#define STORM_FORMULA_LTL_UNTIL_H_
#include "AbstractLtlFormula.h"
#include "src/formula/abstract/Until.h"
#include "src/formula/AbstractFormulaChecker.h"
namespace storm {
namespace property {
namespace ltl {
template <class T> class Until;
/*!
* @brief Interface class for model checkers that support Until.
*
* All model checkers that support the formula class Until must inherit
* this pure virtual class.
*/
template <class T>
class IUntilModelChecker {
public:
/*!
* @brief Evaluates Until formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkUntil(const Until<T>& obj) const = 0;
};
/*!
* @brief Interface class for visitors that support Until.
*
* All visitors that support the formula class Until must inherit
* this pure virtual class.
*/
template <class T>
class IUntilVisitor {
public:
/*!
* @brief Visits Until formula.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual void visitUntil(const Until<T>& obj) = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with an Until node as root.
*
* Has two Abstract LTL formulas as sub formulas/trees.
*
* @par Semantics
* The formula holds iff eventually, formula \e right (the right subtree) holds, and before,
* \e left holds always.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractLtlFormula
*/
template <class T>
class Until : public storm::property::abstract::Until<T, AbstractLtlFormula<T>>,
public AbstractLtlFormula<T> {
public:
/*!
* Empty constructor
*/
Until() {
// Intentionally left empty
}
/*!
* Constructor
*
* @param left The left formula subtree
* @param right The left formula subtree
*/
Until(AbstractLtlFormula<T>* left, AbstractLtlFormula<T>* right)
: storm::property::abstract::Until<T, AbstractLtlFormula<T>>(left, right) {
// Intentionally left empty
}
/*!
* Destructor.
*
* Also deletes the subtrees.
* (this behaviour can be prevented by setting the subtrees to NULL before deletion)
*/
virtual ~Until() {
// Intentionally left empty
}
/*!
* @brief Return string representation of this formula.
*
* In LTL, brackets are needed around the until, as Until may appear nested (in other logics, Until always is the
* root of a path formula); hence this function is overwritten in this class.
*
* @return A string representation of the formula.
*/
virtual std::string toString() const {
return "(" + storm::property::abstract::Until<T, AbstractLtlFormula<T>>::toString() + ")";
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new BoundedUntil-object that is identical the called object.
*/
virtual AbstractLtlFormula<T>* clone() const override {
Until<T>* result = new Until();
if (this->leftIsSet()) {
result->setLeft(this->getLeft().clone());
}
if (this->rightIsSet()) {
result->setRight(this->getRight().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::ltl::AbstractModelChecker<T>& modelChecker) const {
return modelChecker.template as<IUntilModelChecker>()->checkUntil(*this);
}
virtual void visit(visitor::AbstractLtlFormulaVisitor<T>& visitor) const override {
visitor.template as<IUntilVisitor>()->visitUntil(*this);
}
};
} //namespace ltl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_LTL_UNTIL_H_ */

16
src/formula/Ltl/visitor/AbstractLtlFormulaVisitor.cpp

@ -1,16 +0,0 @@
/*
* AbstractLtlFormulaVisitor.cpp
*
* Created on: 29.05.2013
* Author: thomas
*/
#include "AbstractLtlFormulaVisitor.h"
namespace storm {
namespace property {
namespace visitor {
} /* namespace visitor */
} /* namespace property */
} /* namespace storm */

72
src/formula/Ltl/visitor/AbstractLtlFormulaVisitor.h

@ -1,72 +0,0 @@
/*
* AbstractLtlFormulaVisitor.h
*
* Created on: 29.05.2013
* Author: thomas
*/
#ifndef STORM_PROPERTY_LTL_VISITOR_ABSTRACTLTLFORMULAVISITOR_H_
#define STORM_PROPERTY_LTL_VISITOR_ABSTRACTLTLFORMULAVISITOR_H_
// Forward declaration of visitor
namespace storm {
namespace property {
namespace ltl {
namespace visitor {
template <class T>
class AbstractLtlFormulaVisitor;
} /* namespace visitor */
}
}
}
#include "../AbstractLtlFormula.h"
#include "log4cplus/logger.h"
#include "log4cplus/loggingmacros.h"
#include <typeinfo>
extern log4cplus::Logger logger;
namespace storm {
namespace property {
namespace ltl {
namespace visitor {
template <class T>
class AbstractLtlFormulaVisitor {
public:
virtual ~AbstractLtlFormulaVisitor() {
// TODO Auto-generated destructor stub
}
/*!
* Returns a pointer to the model checker object that is of the requested type as given by the template parameters.
* @returns A pointer to the model checker object that is of the requested type as given by the template parameters.
* If the model checker is not of the requested type, type casting will fail and result in an exception.
*/
template <template <class Type> class Target>
Target<T>* as() {
try {
Target<T>* target = dynamic_cast<Target<T>*>(this);
return target;
} catch (std::bad_cast& bc) {
LOG4CPLUS_ERROR(logger, "Bad cast: tried to cast " << typeid(*this).name() << " to " << typeid(Target<T>).name() << ".");
throw bc;
}
return nullptr;
}
void visit(storm::property::ltl::AbstractLtlFormula<T> const& formula) {
formula.visit(*this);
}
};
} /* namespace visitor */
} /* namespace ltl*/
} /* namespace property */
} /* namespace storm */
#endif /* STORM_PROPERTY_LTL_VISITOR_ABSTRACTLTLFORMULAVISITOR_H_ */

42
src/formula/Prctl.h

@ -1,42 +0,0 @@
/*
* Prctl.h
*
* Created on: 06.12.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_PRCTL_H_
#define STORM_FORMULA_PRCTL_H_
#include "modelchecker/prctl/ForwardDeclarations.h"
#include "Prctl/And.h"
#include "Prctl/Ap.h"
#include "Prctl/BoundedUntil.h"
#include "Prctl/BoundedNaryUntil.h"
#include "Prctl/Next.h"
#include "Prctl/Not.h"
#include "Prctl/Or.h"
#include "Prctl/ProbabilisticNoBoundOperator.h"
#include "Prctl/ProbabilisticBoundOperator.h"
#include "Prctl/Until.h"
#include "Prctl/Eventually.h"
#include "Prctl/Globally.h"
#include "Prctl/BoundedEventually.h"
#include "Prctl/InstantaneousReward.h"
#include "Prctl/CumulativeReward.h"
#include "Prctl/ReachabilityReward.h"
#include "Prctl/RewardBoundOperator.h"
#include "Prctl/RewardNoBoundOperator.h"
#include "Prctl/SteadyStateReward.h"
#include "Prctl/AbstractPrctlFormula.h"
#include "Prctl/AbstractStateFormula.h"
#include "Prctl/AbstractNoBoundOperator.h"
#include "Prctl/AbstractPathFormula.h"
#include "modelchecker/prctl/AbstractModelChecker.h"
#endif /* STORM_FORMULA_PRCTL_H_ */

83
src/formula/Prctl/AbstractNoBoundOperator.h

@ -1,83 +0,0 @@
/*
* AbstractNoBoundOperator.h
*
* Created on: 16.04.2013
* Author: thomas
*/
#ifndef STORM_FORMULA_PRCTL_ABSTRACTNOBOUNDOPERATOR_H_
#define STORM_FORMULA_PRCTL_ABSTRACTNOBOUNDOPERATOR_H_
#include "AbstractPrctlFormula.h"
#include "src/formula/abstract/IOptimizingOperator.h"
namespace storm {
namespace property {
namespace prctl {
template <class T>
class AbstractNoBoundOperator;
/*!
* @brief Interface class for model checkers that support PathNoBoundOperator.
*
* All model checkers that support the formula class NoBoundOperator must inherit
* this pure virtual class.
*/
template <class T>
class INoBoundOperatorModelChecker {
public:
/*!
* @brief Evaluates NoBoundOperator formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkNoBoundOperator(const AbstractNoBoundOperator<T>& obj) const = 0;
};
/*!
* Interface class for all PRCTL No bound operators
*/
template <class T>
class AbstractNoBoundOperator: public AbstractPrctlFormula<T>,
public virtual storm::property::abstract::IOptimizingOperator {
public:
AbstractNoBoundOperator() {
// Intentionally left empty.
}
virtual ~AbstractNoBoundOperator() {
// Intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @note This function is not implemented in this class.
* @returns a new AND-object that is identical the called object.
*/
virtual AbstractNoBoundOperator<T>* clone() const = 0;
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @note This function is not implemented in this class.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::prctl::AbstractModelChecker<T>& modelChecker, bool qualitative=false) const = 0;
};
} /* namespace prctl */
} /* namespace property */
} /* namespace storm */
#endif /* STORM_FORMULA_PRCTL_ABSTRACTNOBOUNDOPERATOR_H_ */

31
src/formula/Prctl/AbstractPrctlFormula.h

@ -1,31 +0,0 @@
/*
* AbstractPrctlFormula.h
*
* Created on: 16.04.2013
* Author: thomas
*/
#ifndef STORM_FORMULA_PRCTL_ABSTRACTPRCTLFORMULA_H_
#define STORM_FORMULA_PRCTL_ABSTRACTPRCTLFORMULA_H_
#include "src/formula/abstract/AbstractFormula.h"
namespace storm {
namespace property {
namespace prctl {
/*!
* Interface class for all PRCTL root formulas.
*/
template<class T>
class AbstractPrctlFormula : public virtual storm::property::abstract::AbstractFormula<T> {
public:
virtual ~AbstractPrctlFormula() {
// Intentionally left empty
}
};
} /* namespace prctl */
} /* namespace property */
} /* namespace storm */
#endif /* ABSTRACTPRCTLFORMULA_H_ */

129
src/formula/Prctl/And.h

@ -1,129 +0,0 @@
/*
* And.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_PRCTL_AND_H_
#define STORM_FORMULA_PRCTL_AND_H_
#include "AbstractStateFormula.h"
#include "src/formula/abstract/And.h"
#include "src/formula/AbstractFormulaChecker.h"
#include "src/modelchecker/prctl/ForwardDeclarations.h"
#include <string>
namespace storm {
namespace property {
namespace prctl {
template <class T> class And;
/*!
* @brief Interface class for model checkers that support And.
*
* All model checkers that support the formula class And must inherit
* this pure virtual class.
*/
template <class T>
class IAndModelChecker {
public:
/*!
* @brief Evaluates And formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual storm::storage::BitVector checkAnd(const And<T>& obj) const = 0;
};
/*!
* @brief
* Class for an abstract formula tree with AND node as root.
*
* Has two Abstract state formulas as sub formulas/trees.
*
* As AND is commutative, the order is \e theoretically not important, but will influence the order in which
* the model checker works.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractStateFormula
* @see AbstractPrctlFormula
*/
template <class T>
class And : public storm::property::abstract::And<T, AbstractStateFormula<T>>, public AbstractStateFormula<T> {
public:
/*!
* Empty constructor.
* Will create an AND-node without subnotes. Will not represent a complete formula!
*/
And() {
//intentionally left empty
}
/*!
* Constructor.
* Creates an AND note with the parameters as subtrees.
*
* @param left The left sub formula
* @param right The right sub formula
*/
And(AbstractStateFormula<T>* left, AbstractStateFormula<T>* right)
: storm::property::abstract::And<T, AbstractStateFormula<T>>(left, right) {
//intentionally left empty
}
/*!
* Destructor.
*
* The subtrees are deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*/
virtual ~And() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new AND-object that is identical the called object.
*/
virtual AbstractStateFormula<T>* clone() const override {
And<T>* result = new And();
if (this->leftIsSet()) {
result->setLeft(this->getLeft().clone());
}
if (this->rightIsSet()) {
result->setRight(this->getRight().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A bit vector indicating all states that satisfy the formula represented by the called object.
*/
virtual storm::storage::BitVector check(const storm::modelchecker::prctl::AbstractModelChecker<T>& modelChecker) const override {
return modelChecker.template as<IAndModelChecker>()->checkAnd(*this);
}
};
} //namespace prctl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_PRCTL_AND_H_ */

106
src/formula/Prctl/Ap.h

@ -1,106 +0,0 @@
/*
* Ap.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_PRCTL_AP_H_
#define STORM_FORMULA_PRCTL_AP_H_
#include "AbstractStateFormula.h"
#include "src/formula/abstract/Ap.h"
#include "src/formula/AbstractFormulaChecker.h"
#include "src/modelchecker/prctl/ForwardDeclarations.h"
namespace storm {
namespace property {
namespace prctl {
template <class T> class Ap;
/*!
* @brief Interface class for model checkers that support Ap.
*
* All model checkers that support the formula class Ap must inherit
* this pure virtual class.
*/
template <class T>
class IApModelChecker {
public:
/*!
* @brief Evaluates Ap formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual storm::storage::BitVector checkAp(const Ap<T>& obj) const = 0;
};
/*!
* @brief
* Class for an abstract formula tree with atomic proposition as root.
*
* This class represents the leaves in the formula tree.
*
* @see AbstractPrctlFormula
* @see AbstractStateFormula
*/
template <class T>
class Ap : public storm::property::abstract::Ap<T>,
public AbstractStateFormula<T> {
public:
/*!
* Constructor
*
* Creates a new atomic proposition leaf, with the label Ap
*
* @param ap The string representing the atomic proposition
*/
Ap(std::string ap)
: storm::property::abstract::Ap<T>(ap) {
// Intentionally left empty
}
/*!
* Destructor.
* At this time, empty...
*/
virtual ~Ap() {
// Intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new AND-object that is identical the called object.
*/
virtual AbstractStateFormula<T>* clone() const override {
return new Ap(this->getAp());
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A bit vector indicating all states that satisfy the formula represented by the called object.
*/
virtual storm::storage::BitVector check(const storm::modelchecker::prctl::AbstractModelChecker<T>& modelChecker) const override {
return modelChecker.template as<IApModelChecker>()->checkAp(*this);
}
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_PRCTL_AP_H_ */

126
src/formula/Prctl/BoundedEventually.h

@ -1,126 +0,0 @@
/*
* BoundedUntil.h
*
* Created on: 27.11.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_PRCTL_BOUNDEDEVENTUALLY_H_
#define STORM_FORMULA_PRCTL_BOUNDEDEVENTUALLY_H_
#include "src/formula/abstract/BoundedEventually.h"
#include "src/formula/Prctl/AbstractPathFormula.h"
#include "src/formula/Prctl/AbstractStateFormula.h"
#include "src/formula/AbstractFormulaChecker.h"
#include <cstdint>
#include <string>
#include "src/modelchecker/prctl/ForwardDeclarations.h"
namespace storm {
namespace property {
namespace prctl{
template <class T> class BoundedEventually;
/*!
* @brief Interface class for model checkers that support BoundedEventually.
*
* All model checkers that support the formula class BoundedEventually must inherit
* this pure virtual class.
*/
template <class T>
class IBoundedEventuallyModelChecker {
public:
/*!
* @brief Evaluates BoundedEventually formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkBoundedEventually(const BoundedEventually<T>& obj, bool qualitative) const = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with a BoundedEventually node as root.
*
* Has one Abstract state formulas as sub formula/tree.
*
* @par Semantics
* The formula holds iff in at most \e bound steps, formula \e child holds.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractPathFormula
* @see AbstractPrctlFormula
*/
template <class T>
class BoundedEventually : public storm::property::abstract::BoundedEventually<T, AbstractStateFormula<T>>,
public AbstractPathFormula<T> {
public:
/*!
* Empty constructor
*/
BoundedEventually() {
//intentionally left empty
}
/*!
* Constructor
*
* @param child The child formula subtree
* @param bound The maximal number of steps
*/
BoundedEventually(AbstractStateFormula<T>* child, uint_fast64_t bound) :
storm::property::abstract::BoundedEventually<T, AbstractStateFormula<T>>(child, bound){
//intentionally left empty
}
/*!
* Destructor.
*
* Also deletes the subtrees.
* (this behaviour can be prevented by setting the subtrees to NULL before deletion)
*/
virtual ~BoundedEventually() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new BoundedUntil-object that is identical the called object.
*/
virtual AbstractPathFormula<T>* clone() const override {
BoundedEventually<T>* result = new BoundedEventually<T>();
result->setBound(this->getBound());
if (this->childIsSet()) {
result->setChild(this->getChild().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::prctl::AbstractModelChecker<T>& modelChecker, bool qualitative) const override {
return modelChecker.template as<IBoundedEventuallyModelChecker>()->checkBoundedEventually(*this, qualitative);
}
};
} //namespace prctl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_PRCTL_BOUNDEDUNTIL_H_ */

141
src/formula/Prctl/BoundedNaryUntil.h

@ -1,141 +0,0 @@
/*
* BoundedNaryUntil.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_PRCTL_BOUNDEDNARYUNTIL_H_
#define STORM_FORMULA_PRCTL_BOUNDEDNARYUNTIL_H_
#include "src/formula/abstract/BoundedNaryUntil.h"
#include "src/formula/Prctl/AbstractPathFormula.h"
#include "src/formula/Prctl/AbstractStateFormula.h"
#include <cstdint>
#include <string>
#include <vector>
#include <tuple>
#include <sstream>
#include "src/modelchecker/prctl/ForwardDeclarations.h"
namespace storm {
namespace property {
namespace prctl {
template <class T> class BoundedNaryUntil;
/*!
* @brief Interface class for model checkers that support BoundedNaryUntil.
*
* All model checkers that support the formula class BoundedNaryUntil must inherit
* this pure virtual class.
*/
template <class T>
class IBoundedNaryUntilModelChecker {
public:
/*!
* @brief Evaluates BoundedNaryUntil formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkBoundedNaryUntil(const BoundedNaryUntil<T>& obj, bool qualitative) const = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with a BoundedNaryUntil node as root.
*
* Has at least two Abstract state formulas as sub formulas and an interval
* associated with all but the first sub formula. We'll call the first one
* \e left and all other one \e right.
*
* @par Semantics
* The formula holds iff \e left holds until eventually any of the \e right
* formulas holds after a number of steps contained in the interval
* associated with this formula.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractPathFormula
* @see AbstractPrctlFormula
*/
template <class T>
class BoundedNaryUntil : public storm::property::abstract::BoundedNaryUntil<T, AbstractStateFormula<T>>,
public AbstractPathFormula<T> {
public:
/*!
* Empty constructor
*/
BoundedNaryUntil() {
}
/*!
* Constructor
*
* @param left The left formula subtree
* @param right The left formula subtree
*/
BoundedNaryUntil(AbstractStateFormula<T>* left, std::vector<std::tuple<AbstractStateFormula<T>*,T,T>>* right) :
storm::property::abstract::BoundedNaryUntil<T, AbstractStateFormula<T>>(left, right){
}
/*!
* Destructor.
*
* Also deletes the subtrees.
* (this behaviour can be prevented by setting the subtrees to NULL before deletion)
*/
virtual ~BoundedNaryUntil() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new BoundedNaryUntil-object that is identical the called object.
*/
virtual AbstractPathFormula<T>* clone() const override {
BoundedNaryUntil<T>* result = new BoundedNaryUntil<T>();
if (this->leftIsSet()) {
result->setLeft(this->getLeft().clone());
}
if (this->rightIsSet()) {
std::vector<std::tuple<AbstractStateFormula<T>*,T,T>>* newright = new std::vector<std::tuple<AbstractStateFormula<T>*,T,T>>();
for (auto it = this->right->begin(); it != this->right->end(); ++it) {
newright->push_back(std::tuple<AbstractStateFormula<T>*,T,T>(std::get<0>(*it)->clone(), std::get<1>(*it), std::get<2>(*it)));
}
result->setRight(newright);
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::prctl::AbstractModelChecker<T>& modelChecker, bool qualitative) const override {
return modelChecker.template as<IBoundedNaryUntilModelChecker>()->checkBoundedNaryUntil(*this, qualitative);
}
};
} //namespace prctl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_PRCTL_BOUNDEDNARYUNTIL_H_ */

131
src/formula/Prctl/BoundedUntil.h

@ -1,131 +0,0 @@
/*
* BoundedUntil.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_PRCTL_BOUNDEDUNTIL_H_
#define STORM_FORMULA_PRCTL_BOUNDEDUNTIL_H_
#include "src/formula/abstract/BoundedUntil.h"
#include "src/formula/Prctl/AbstractPathFormula.h"
#include "src/formula/Prctl/AbstractStateFormula.h"
#include <cstdint>
#include <string>
#include "src/modelchecker/prctl/ForwardDeclarations.h"
namespace storm {
namespace property {
namespace prctl {
template <class T> class BoundedUntil;
/*!
* @brief Interface class for model checkers that support BoundedUntil.
*
* All model checkers that support the formula class BoundedUntil must inherit
* this pure virtual class.
*/
template <class T>
class IBoundedUntilModelChecker {
public:
/*!
* @brief Evaluates BoundedUntil formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkBoundedUntil(const BoundedUntil<T>& obj, bool qualitative) const = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with a BoundedUntil node as root.
*
* Has two Abstract state formulas as sub formulas/trees.
*
* @par Semantics
* The formula holds iff in at most \e bound steps, formula \e right (the right subtree) holds, and before,
* \e left holds.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractPathFormula
* @see AbstractPrctlFormula
*/
template <class T>
class BoundedUntil : public storm::property::abstract::BoundedUntil<T, AbstractStateFormula<T>>,
public AbstractPathFormula<T> {
public:
/*!
* Empty constructor
*/
BoundedUntil() {
//Intentionally left empty
}
/*!
* Constructor
*
* @param left The left formula subtree
* @param right The left formula subtree
* @param bound The maximal number of steps
*/
BoundedUntil(AbstractStateFormula<T>* left, AbstractStateFormula<T>* right,
uint_fast64_t bound) :
storm::property::abstract::BoundedUntil<T, AbstractStateFormula<T>>(left,right,bound) {
//intentionally left empty
}
/*!
* Destructor.
*
* Also deletes the subtrees.
* (this behaviour can be prevented by setting the subtrees to NULL before deletion)
*/
virtual ~BoundedUntil() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new BoundedUntil-object that is identical the called object.
*/
virtual AbstractPathFormula<T>* clone() const override {
BoundedUntil<T>* result = new BoundedUntil<T>();
result->setBound(this->getBound());
if (this->leftIsSet()) {
result->setLeft(this->getLeft().clone());
}
if (this->rightIsSet()) {
result->setRight(this->getRight().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::prctl::AbstractModelChecker<T>& modelChecker, bool qualitative) const override {
return modelChecker.template as<IBoundedUntilModelChecker>()->checkBoundedUntil(*this, qualitative);
}
};
} //namespace prctl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_PRCTL_BOUNDEDUNTIL_H_ */

110
src/formula/Prctl/CumulativeReward.h

@ -1,110 +0,0 @@
/*
* InstantaneousReward.h
*
* Created on: 26.12.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_PRCTL_CUMULATIVEREWARD_H_
#define STORM_FORMULA_PRCTL_CUMULATIVEREWARD_H_
#include "AbstractPathFormula.h"
#include "AbstractStateFormula.h"
#include "src/formula/abstract/CumulativeReward.h"
#include "src/formula/AbstractFormulaChecker.h"
#include <string>
namespace storm {
namespace property {
namespace prctl {
template <class T> class CumulativeReward;
/*!
* @brief Interface class for model checkers that support CumulativeReward.
*
* All model checkers that support the formula class CumulativeReward must inherit
* this pure virtual class.
*/
template <class T>
class ICumulativeRewardModelChecker {
public:
/*!
* @brief Evaluates CumulativeReward formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkCumulativeReward(const CumulativeReward<T>& obj, bool qualitative) const = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with a Cumulative Reward node as root.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractPathFormula
* @see AbstractPrctlFormula
*/
template <class T>
class CumulativeReward : public storm::property::abstract::CumulativeReward<T>,
public AbstractPathFormula<T> {
public:
/*!
* Empty constructor
*/
CumulativeReward() {
// Intentionally left empty
}
/*!
* Constructor
*
* @param bound The time bound of the reward formula
*/
CumulativeReward(T bound) :
storm::property::abstract::CumulativeReward<T>(bound) {
// Intentionally left empty
}
/*!
* Empty destructor.
*/
virtual ~CumulativeReward() {
// Intentionally left empty.
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new CumulativeReward-object that is identical the called object.
*/
virtual AbstractPathFormula<T>* clone() const override {
return new CumulativeReward(this->getBound());
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::prctl::AbstractModelChecker<T>& modelChecker, bool qualitative) const override {
return modelChecker.template as<ICumulativeRewardModelChecker>()->checkCumulativeReward(*this, qualitative);
}
};
} //namespace prctl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_PRCTL_INSTANTANEOUSREWARD_H_ */

120
src/formula/Prctl/Eventually.h

@ -1,120 +0,0 @@
/*
* Next.h
*
* Created on: 26.12.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_PRCTL_EVENTUALLY_H_
#define STORM_FORMULA_PRCTL_EVENTUALLY_H_
#include "src/formula/abstract/Eventually.h"
#include "src/formula/Prctl/AbstractPathFormula.h"
#include "src/formula/Prctl/AbstractStateFormula.h"
#include "src/modelchecker/prctl/ForwardDeclarations.h"
namespace storm {
namespace property {
namespace prctl {
template <class T> class Eventually;
/*!
* @brief Interface class for model checkers that support Eventually.
*
* All model checkers that support the formula class Eventually must inherit
* this pure virtual class.
*/
template <class T>
class IEventuallyModelChecker {
public:
/*!
* @brief Evaluates Eventually formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkEventually(const Eventually<T>& obj, bool qualitative) const = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with an Eventually node as root.
*
* Has one Abstract state formula as sub formula/tree.
*
* @par Semantics
* The formula holds iff eventually \e child holds.
*
* The subtree is seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to nullptr before deletion)
*
* @see AbstractPathFormula
* @see AbstractPrctlFormula
*/
template <class T>
class Eventually : public storm::property::abstract::Eventually<T, AbstractStateFormula<T>>,
public AbstractPathFormula<T> {
public:
/*!
* Empty constructor
*/
Eventually() {
// Intentionally left empty
}
/*!
* Constructor
*
* @param child The child node
*/
Eventually(AbstractStateFormula<T>* child)
: storm::property::abstract::Eventually<T, AbstractStateFormula<T>>(child) {
}
/*!
* Constructor.
*
* Also deletes the subtree.
* (this behaviour can be prevented by setting the subtrees to nullptr before deletion)
*/
virtual ~Eventually() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new Eventually-object that is identical the called object.
*/
virtual AbstractPathFormula<T>* clone() const override {
Eventually<T>* result = new Eventually<T>();
if (this->childIsSet()) {
result->setChild(this->getChild().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::prctl::AbstractModelChecker<T>& modelChecker, bool qualitative) const override {
return modelChecker.template as<IEventuallyModelChecker>()->checkEventually(*this, qualitative);
}
};
} //namespace prctl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_PRCTL_EVENTUALLY_H_ */

122
src/formula/Prctl/Globally.h

@ -1,122 +0,0 @@
/*
* Next.h
*
* Created on: 26.12.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_PRCTL_GLOBALLY_H_
#define STORM_FORMULA_PRCTL_GLOBALLY_H_
#include "src/formula/abstract/Globally.h"
#include "AbstractPathFormula.h"
#include "AbstractStateFormula.h"
#include "src/formula/AbstractFormulaChecker.h"
#include "src/modelchecker/prctl/ForwardDeclarations.h"
namespace storm {
namespace property {
namespace prctl {
template <class T> class Globally;
/*!
* @brief Interface class for model checkers that support Globally.
*
* All model checkers that support the formula class Globally must inherit
* this pure virtual class.
*/
template <class T>
class IGloballyModelChecker {
public:
/*!
* @brief Evaluates Globally formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkGlobally(const Globally<T>& obj, bool qualitative) const = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with a Globally node as root.
*
* Has one Abstract state formula as sub formula/tree.
*
* @par Semantics
* The formula holds iff globally \e child holds.
*
* The subtree is seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to nullptr before deletion)
*
* @see AbstractPathFormula
* @see AbstractPrctlFormula
*/
template <class T>
class Globally : public storm::property::abstract::Globally<T, AbstractStateFormula<T>>,
public AbstractPathFormula<T> {
public:
/*!
* Empty constructor
*/
Globally() {
//intentionally left empty
}
/*!
* Constructor
*
* @param child The child node
*/
Globally(AbstractStateFormula<T>* child)
: storm::property::abstract::Globally<T, AbstractStateFormula<T>>(child) {
//intentionally left empty
}
/*!
* Constructor.
*
* Also deletes the subtree.
* (this behaviour can be prevented by setting the subtrees to nullptr before deletion)
*/
virtual ~Globally() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new Globally-object that is identical the called object.
*/
virtual AbstractPathFormula<T>* clone() const override {
Globally<T>* result = new Globally<T>();
if (this->childIsSet()) {
result->setChild(this->getChild().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::prctl::AbstractModelChecker<T>& modelChecker, bool qualitative) const override {
return modelChecker.template as<IGloballyModelChecker>()->checkGlobally(*this, qualitative);
}
};
} //namespace prctl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_PRCTL_GLOBALLY_H_ */

111
src/formula/Prctl/InstantaneousReward.h

@ -1,111 +0,0 @@
/*
* InstantaneousReward.h
*
* Created on: 26.12.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_PRCTL_INSTANTANEOUSREWARD_H_
#define STORM_FORMULA_PRCTL_INSTANTANEOUSREWARD_H_
#include "AbstractPathFormula.h"
#include "AbstractStateFormula.h"
#include "src/formula/abstract/InstantaneousReward.h"
#include "src/formula/AbstractFormulaChecker.h"
#include <cstdint>
#include <string>
namespace storm {
namespace property {
namespace prctl {
template <class T> class InstantaneousReward;
/*!
* @brief Interface class for model checkers that support InstantaneousReward.
*
* All model checkers that support the formula class InstantaneousReward must inherit
* this pure virtual class.
*/
template <class T>
class IInstantaneousRewardModelChecker {
public:
/*!
* @brief Evaluates InstantaneousReward formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkInstantaneousReward(const InstantaneousReward<T>& obj, bool qualitative) const = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with a Instantaneous Reward node as root.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractPathFormula
* @see AbstractPrctlFormula
*/
template <class T>
class InstantaneousReward : public storm::property::abstract::InstantaneousReward<T>,
public AbstractPathFormula<T> {
public:
/*!
* Empty constructor
*/
InstantaneousReward() {
//intentionally left empty
}
/*!
* Constructor
*
* @param bound The time instance of the reward formula
*/
InstantaneousReward(uint_fast64_t bound) :
storm::property::abstract::InstantaneousReward<T>(bound) {
//intentionally left empty
}
/*!
* Empty destructor.
*/
virtual ~InstantaneousReward() {
// Intentionally left empty.
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new InstantaneousReward-object that is identical the called object.
*/
virtual AbstractPathFormula<T>* clone() const override {
return new InstantaneousReward(this->getBound());
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::prctl::AbstractModelChecker<T>& modelChecker, bool qualitative) const override {
return modelChecker.template as<IInstantaneousRewardModelChecker>()->checkInstantaneousReward(*this, qualitative);
}
};
} //namespace prctl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_PRCTL_INSTANTANEOUSREWARD_H_ */

120
src/formula/Prctl/Next.h

@ -1,120 +0,0 @@
/*
* Next.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_PRCTL_NEXT_H_
#define STORM_FORMULA_PRCTL_NEXT_H_
#include "AbstractPathFormula.h"
#include "AbstractStateFormula.h"
#include "src/formula/abstract/Next.h"
#include "src/formula/AbstractFormulaChecker.h"
namespace storm {
namespace property {
namespace prctl {
template <class T> class Next;
/*!
* @brief Interface class for model checkers that support Next.
*
* All model checkers that support the formula class Next must inherit
* this pure virtual class.
*/
template <class T>
class INextModelChecker {
public:
/*!
* @brief Evaluates Next formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkNext(const Next<T>& obj, bool qualitative) const = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with a Next node as root.
*
* Has two Abstract state formulas as sub formulas/trees.
*
* @par Semantics
* The formula holds iff in the next step, \e child holds
*
* The subtree is seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractPathFormula
* @see AbstractPrctlFormula
*/
template <class T>
class Next : public storm::property::abstract::Next<T, AbstractStateFormula<T>>,
public AbstractPathFormula<T> {
public:
/*!
* Empty constructor
*/
Next() {
//intentionally left empty
}
/*!
* Constructor
*
* @param child The child node
*/
Next(AbstractStateFormula<T>* child)
: storm::property::abstract::Next<T, AbstractStateFormula<T>>(child) {
//intentionally left empty
}
/*!
* Constructor.
*
* Also deletes the subtree.
* (this behaviour can be prevented by setting the subtrees to NULL before deletion)
*/
virtual ~Next() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new BoundedUntil-object that is identical the called object.
*/
virtual AbstractPathFormula<T>* clone() const override {
Next<T>* result = new Next<T>();
if (this->childIsSet()) {
result->setChild(this->getChild().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::prctl::AbstractModelChecker<T>& modelChecker, bool qualitative) const override {
return modelChecker.template as<INextModelChecker>()->checkNext(*this, qualitative);
}
};
} //namespace prctl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_PRCTL_NEXT_H_ */

116
src/formula/Prctl/Not.h

@ -1,116 +0,0 @@
/*
* Not.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_PRCTL_NOT_H_
#define STORM_FORMULA_PRCTL_NOT_H_
#include "AbstractStateFormula.h"
#include "src/formula/abstract/Not.h"
#include "src/formula/AbstractFormulaChecker.h"
#include "src/modelchecker/prctl/ForwardDeclarations.h"
namespace storm {
namespace property {
namespace prctl {
template <class T> class Not;
/*!
* @brief Interface class for model checkers that support Not.
*
* All model checkers that support the formula class Not must inherit
* this pure virtual class.
*/
template <class T>
class INotModelChecker {
public:
/*!
* @brief Evaluates Not formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual storm::storage::BitVector checkNot(const Not<T>& obj) const = 0;
};
/*!
* @brief
* Class for an abstract formula tree with NOT node as root.
*
* Has one Abstract state formula as sub formula/tree.
*
* The subtree is seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractStateFormula
* @see AbstractPrctlFormula
*/
template <class T>
class Not : public storm::property::abstract::Not<T, AbstractStateFormula<T>>,
public AbstractStateFormula<T> {
public:
/*!
* Empty constructor
*/
Not() {
//intentionally left empty
}
/*!
* Constructor
* @param child The child node
*/
Not(AbstractStateFormula<T>* child) :
storm::property::abstract::Not<T, AbstractStateFormula<T>>(child){
//intentionally left empty
}
/*!
* Destructor
*
* Also deletes the subtree
* (this behavior can be prevented by setting them to NULL before deletion)
*/
virtual ~Not() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new AND-object that is identical the called object.
*/
virtual AbstractStateFormula<T>* clone() const override {
Not<T>* result = new Not<T>();
if (this->childIsSet()) {
result->setChild(this->getChild().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A bit vector indicating all states that satisfy the formula represented by the called object.
*/
virtual storm::storage::BitVector check(const storm::modelchecker::prctl::AbstractModelChecker<T>& modelChecker) const override {
return modelChecker.template as<INotModelChecker>()->checkNot(*this);
}
};
} //namespace prctl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_PRCTL_NOT_H_ */

125
src/formula/Prctl/Or.h

@ -1,125 +0,0 @@
/*
* Or.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_PRCTL_OR_H_
#define STORM_FORMULA_PRCTL_OR_H_
#include "AbstractStateFormula.h"
#include "src/formula/abstract/Or.h"
#include "src/formula/AbstractFormulaChecker.h"
namespace storm {
namespace property {
namespace prctl {
template <class T> class Or;
/*!
* @brief Interface class for model checkers that support Or.
*
* All model checkers that support the formula class Or must inherit
* this pure virtual class.
*/
template <class T>
class IOrModelChecker {
public:
/*!
* @brief Evaluates Or formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual storm::storage::BitVector checkOr(const Or<T>& obj) const = 0;
};
/*!
* @brief
* Class for an abstract formula tree with OR node as root.
*
* Has two Abstract state formulas as sub formulas/trees.
*
* As OR is commutative, the order is \e theoretically not important, but will influence the order in which
* the model checker works.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractStateFormula
* @see AbstractPrctlFormula
*/
template <class T>
class Or : public storm::property::abstract::Or<T, AbstractStateFormula<T>>,
public AbstractStateFormula<T> {
public:
/*!
* Empty constructor.
* Will create an OR-node without subnotes. The result does not represent a complete formula!
*/
Or() {
//intentionally left empty
}
/*!
* Constructor.
* Creates an OR note with the parameters as subtrees.
*
* @param left The left sub formula
* @param right The right sub formula
*/
Or(AbstractStateFormula<T>* left, AbstractStateFormula<T>* right) :
storm::property::abstract::Or<T, AbstractStateFormula<T>>(left, right) {
//intentionally left empty
}
/*!
* Destructor.
*
* The subtrees are deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*/
virtual ~Or() {
//intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new AND-object that is identical the called object.
*/
virtual AbstractStateFormula<T>* clone() const override {
Or<T>* result = new Or();
if (this->leftIsSet()) {
result->setLeft(this->getLeft().clone());
}
if (this->rightIsSet()) {
result->setRight(this->getRight().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A bit vector indicating all states that satisfy the formula represented by the called object.
*/
virtual storm::storage::BitVector check(const storm::modelchecker::prctl::AbstractModelChecker<T>& modelChecker) const override {
return modelChecker.template as<IOrModelChecker>()->checkOr(*this);
}
};
} //namespace prctl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_PRCTL_OR_H_ */

139
src/formula/Prctl/ProbabilisticBoundOperator.h

@ -1,139 +0,0 @@
/*
* ProbabilisticBoundOperator.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_PRCTL_PROBABILISTICBOUNDOPERATOR_H_
#define STORM_FORMULA_PRCTL_PROBABILISTICBOUNDOPERATOR_H_
#include "AbstractStateFormula.h"
#include "AbstractPathFormula.h"
#include "src/formula/abstract/ProbabilisticBoundOperator.h"
#include "utility/constants.h"
namespace storm {
namespace property {
namespace prctl {
template <class T> class ProbabilisticBoundOperator;
/*!
* @brief Interface class for model checkers that support ProbabilisticBoundOperator.
*
* All model checkers that support the formula class PathBoundOperator must inherit
* this pure virtual class.
*/
template <class T>
class IProbabilisticBoundOperatorModelChecker {
public:
virtual storm::storage::BitVector checkProbabilisticBoundOperator(const ProbabilisticBoundOperator<T>& obj) const = 0;
};
/*!
* @brief
* Class for an abstract formula tree with a P (probablistic) operator node over a probability interval
* as root.
*
* Has one Abstract path formula as sub formula/tree.
*
* @par Semantics
* The formula holds iff the probability that the path formula holds is inside the bounds
* specified in this operator
*
* The subtree is seen as part of the object and deleted with it
* (this behavior can be prevented by setting them to NULL before deletion)
*
*
* @see AbstractStateFormula
* @see AbstractPathFormula
* @see ProbabilisticOperator
* @see ProbabilisticNoBoundsOperator
* @see AbstractPrctlFormula
*/
template<class T>
class ProbabilisticBoundOperator : public storm::property::abstract::ProbabilisticBoundOperator<T, AbstractPathFormula<T>>,
public AbstractStateFormula<T> {
public:
/*!
* Empty constructor
*/
ProbabilisticBoundOperator() {
// Intentionally left empty
}
/*!
* Constructor
*
* @param comparisonRelation The relation to compare the actual value and the bound
* @param bound The bound for the probability
* @param pathFormula The child node
*/
ProbabilisticBoundOperator(
storm::property::ComparisonType comparisonRelation,
T bound,
AbstractPathFormula<T>* pathFormula)
: storm::property::abstract::ProbabilisticBoundOperator<T, AbstractPathFormula<T>>(comparisonRelation, bound, pathFormula) {
// Intentionally left empty
}
/*!
*
* @param comparisonRelation
* @param bound
* @param pathFormula
* @param minimumOperator
*/
ProbabilisticBoundOperator(
storm::property::ComparisonType comparisonRelation,
T bound,
AbstractPathFormula<T>* pathFormula,
bool minimumOperator)
: storm::property::abstract::ProbabilisticBoundOperator<T, AbstractPathFormula<T>>(comparisonRelation, bound, pathFormula, minimumOperator){
// Intentionally left empty
}
/*!
*
*/
virtual ~ProbabilisticBoundOperator() {
// Intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new AND-object that is identical the called object.
*/
virtual AbstractStateFormula<T>* clone() const override {
ProbabilisticBoundOperator<T>* result = new ProbabilisticBoundOperator<T>();
result->setComparisonOperator(this->getComparisonOperator());
result->setBound(this->getBound());
result->setPathFormula(this->getPathFormula().clone());
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A bit vector indicating all states that satisfy the formula represented by the called object.
*/
virtual storm::storage::BitVector check(const storm::modelchecker::prctl::AbstractModelChecker<T>& modelChecker) const override {
return modelChecker.template as<IProbabilisticBoundOperatorModelChecker>()->checkProbabilisticBoundOperator(*this);
}
};
} //namespace prctl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_PRCTL_PROBABILISTICBOUNDOPERATOR_H_ */

115
src/formula/Prctl/ProbabilisticNoBoundOperator.h

@ -1,115 +0,0 @@
/*
* ProbabilisticNoBoundOperator.h
*
* Created on: 12.12.2012
* Author: thomas
*/
#ifndef STORM_FORMULA_PRCTL_PROBABILISTICNOBOUNDOPERATOR_H_
#define STORM_FORMULA_PRCTL_PROBABILISTICNOBOUNDOPERATOR_H_
#include "AbstractPathFormula.h"
#include "AbstractNoBoundOperator.h"
#include "src/formula/abstract/ProbabilisticNoBoundOperator.h"
namespace storm {
namespace property {
namespace prctl {
/*!
* @brief
* Class for an abstract formula tree with a P (probablistic) operator without declaration of probabilities
* as root.
*
* Checking a formula with this operator as root returns the probabilities that the path formula holds
* (for each state)
*
* Has one Abstract path formula as sub formula/tree.
*
* @note
* This class is a hybrid of a state and path formula, and may only appear as the outermost operator.
* Hence, it is seen as neither a state nor a path formula, but is directly derived from AbstractFormula.
*
* @note
* This class does not contain a check() method like the other formula classes.
* The check method should only be called by the model checker to infer the correct check function for sub
* formulas. As this operator can only appear at the root, the method is not useful here.
* Use the checkProbabilisticNoBoundOperator method from the DtmcPrctlModelChecker class instead.
*
* The subtree is seen as part of the object and deleted with it
* (this behavior can be prevented by setting them to NULL before deletion)
*
*
* @see AbstractStateFormula
* @see AbstractPathFormula
* @see ProbabilisticOperator
* @see ProbabilisticIntervalOperator
* @see AbstractPrctlFormula
*/
template <class T>
class ProbabilisticNoBoundOperator: public storm::property::abstract::ProbabilisticNoBoundOperator<T, AbstractPathFormula<T>>,
public AbstractNoBoundOperator<T> {
public:
/*!
* Empty constructor
*/
ProbabilisticNoBoundOperator() {
// Intentionally left empty
}
/*!
* Constructor
*
* @param pathFormula The child node.
*/
ProbabilisticNoBoundOperator(AbstractPathFormula<T>* pathFormula)
: storm::property::abstract::ProbabilisticNoBoundOperator<T, AbstractPathFormula<T>>(pathFormula) {
// Intentionally left empty
}
/*!
* Constructor
*
* @param pathFormula The child node.
*/
ProbabilisticNoBoundOperator(AbstractPathFormula<T>* pathFormula, bool minimumOperator)
: storm::property::abstract::ProbabilisticNoBoundOperator<T, AbstractPathFormula<T>>(pathFormula, minimumOperator) {
// Intentionally left empty
}
/*!
* Destructor
*/
virtual ~ProbabilisticNoBoundOperator() {
// Intentionally left empty
}
virtual AbstractNoBoundOperator<T>* clone() const override {
ProbabilisticNoBoundOperator<T>* result = new ProbabilisticNoBoundOperator<T>();
if (this->pathFormulaIsSet()) {
result->setPathFormula(this->getPathFormula().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @note This function is not implemented in this class.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::prctl::AbstractModelChecker<T>& modelChecker, bool qualitative=false) const override {
return this->getPathFormula().check(modelChecker, qualitative);
}
};
} //namespace prctl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_PRCTL_PROBABILISTICNOBOUNDOPERATOR_H_ */

117
src/formula/Prctl/ReachabilityReward.h

@ -1,117 +0,0 @@
/*
* Next.h
*
* Created on: 26.12.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_PRCTL_REACHABILITYREWARD_H_
#define STORM_FORMULA_PRCTL_REACHABILITYREWARD_H_
#include "AbstractPathFormula.h"
#include "AbstractStateFormula.h"
#include "../abstract/Eventually.h"
#include "src/formula/AbstractFormulaChecker.h"
namespace storm {
namespace property {
namespace prctl {
template <class T> class ReachabilityReward;
/*!
* @brief Interface class for model checkers that support ReachabilityReward.
*
* All model checkers that support the formula class ReachabilityReward must inherit
* this pure virtual class.
*/
template <class T>
class IReachabilityRewardModelChecker {
public:
/*!
* @brief Evaluates ReachabilityReward formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkReachabilityReward(const ReachabilityReward<T>& obj, bool qualitative) const = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with an Reachability Reward node as root.
*
* Has one Abstract state formula as sub formula/tree.
*
* The subtree is seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to nullptr before deletion)
*
* @see AbstractPathFormula
* @see AbstractPrctlFormula
*/
template <class T>
class ReachabilityReward : public storm::property::abstract::Eventually<T, AbstractStateFormula<T>>,
public AbstractPathFormula<T> {
public:
/*!
* Empty constructor
*/
ReachabilityReward() {
// Intentionally left empty
}
/*!
* Constructor
*
* @param child The child node
*/
ReachabilityReward(AbstractStateFormula<T>* child) :
storm::property::abstract::Eventually<T, AbstractStateFormula<T>>(child){
// Intentionally left empty
}
/*!
* Constructor.
*
* Also deletes the subtree.
* (this behaviour can be prevented by setting the subtrees to nullptr before deletion)
*/
virtual ~ReachabilityReward() {
// Intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new ReachabilityReward-object that is identical the called object.
*/
virtual AbstractPathFormula<T>* clone() const override {
ReachabilityReward<T>* result = new ReachabilityReward<T>();
if (this->childIsSet()) {
result->setChild(this->getChild().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::prctl::AbstractModelChecker<T>& modelChecker, bool qualitative) const override {
return modelChecker.template as<IReachabilityRewardModelChecker>()->checkReachabilityReward(*this, qualitative);
}
};
} //namespace prctl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_PRCTL_REACHABILITYREWARD_H_ */

132
src/formula/Prctl/RewardBoundOperator.h

@ -1,132 +0,0 @@
/*
* RewardBoundOperator.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_PRCTL_REWARDBOUNDOPERATOR_H_
#define STORM_FORMULA_PRCTL_REWARDBOUNDOPERATOR_H_
#include "AbstractPathFormula.h"
#include "AbstractStateFormula.h"
#include "src/formula/abstract/RewardBoundOperator.h"
#include "utility/constants.h"
namespace storm {
namespace property {
namespace prctl {
template <class T> class RewardBoundOperator;
/*!
* @brief Interface class for model checkers that support RewardBoundOperator.
*
* All model checkers that support the formula class PathBoundOperator must inherit
* this pure virtual class.
*/
template <class T>
class IRewardBoundOperatorModelChecker {
public:
virtual storm::storage::BitVector checkRewardBoundOperator(const RewardBoundOperator<T>& obj) const = 0;
};
/*!
* @brief
* Class for an abstract formula tree with a R (reward) operator node over a reward interval as root.
*
* Has a reward path formula as sub formula/tree.
*
* @par Semantics
* The formula holds iff the reward of the reward path formula is inside the bounds
* specified in this operator
*
* The subtree is seen as part of the object and deleted with it
* (this behavior can be prevented by setting them to NULL before deletion)
*
*
* @see AbstractStateFormula
* @see AbstractPathFormula
* @see ProbabilisticOperator
* @see ProbabilisticNoBoundsOperator
* @see AbstractPrctlFormula
*/
template<class T>
class RewardBoundOperator : public storm::property::abstract::RewardBoundOperator<T, AbstractPathFormula<T>>,
public AbstractStateFormula<T> {
public:
/*!
* Empty constructor
*/
RewardBoundOperator() {
// Intentionally left empty
}
/*!
* Constructor
*
* @param comparisonRelation The relation to compare the actual value and the bound
* @param bound The bound for the probability
* @param pathFormula The child node
*/
RewardBoundOperator(
storm::property::ComparisonType comparisonRelation,
T bound,
AbstractPathFormula<T>* pathFormula) :
storm::property::abstract::RewardBoundOperator<T, AbstractPathFormula<T>>(comparisonRelation, bound, pathFormula) {
// Intentionally left empty
}
/*!
* Constructor
*
* @param comparisonRelation
* @param bound
* @param pathFormula
* @param minimumOperator
*/
RewardBoundOperator(
storm::property::ComparisonType comparisonRelation,
T bound,
AbstractPathFormula<T>* pathFormula,
bool minimumOperator)
: storm::property::abstract::RewardBoundOperator<T, AbstractPathFormula<T>>(comparisonRelation, bound, pathFormula, minimumOperator) {
// Intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new AND-object that is identical the called object.
*/
virtual AbstractStateFormula<T>* clone() const override {
RewardBoundOperator<T>* result = new RewardBoundOperator<T>();
result->setComparisonOperator(this->getComparisonOperator());
result->setBound(this->getBound());
result->setPathFormula(this->getPathFormula().clone());
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A bit vector indicating all states that satisfy the formula represented by the called object.
*/
virtual storm::storage::BitVector check(const storm::modelchecker::prctl::AbstractModelChecker<T>& modelChecker) const override {
return modelChecker.template as<IRewardBoundOperatorModelChecker>()->checkRewardBoundOperator(*this);
}
};
} //namespace prctl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_PRCTL_REWARDBOUNDOPERATOR_H_ */

108
src/formula/Prctl/RewardNoBoundOperator.h

@ -1,108 +0,0 @@
/*
* RewardNoBoundOperator.h
*
* Created on: 25.12.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_PRCTL_REWARDNOBOUNDOPERATOR_H_
#define STORM_FORMULA_PRCTL_REWARDNOBOUNDOPERATOR_H_
#include "AbstractNoBoundOperator.h"
#include "AbstractPathFormula.h"
#include "src/formula/abstract/RewardNoBoundOperator.h"
namespace storm {
namespace property {
namespace prctl {
/*!
* @brief
* Class for an abstract formula tree with a R (reward) operator without declaration of reward values
* as root.
*
* Checking a formula with this operator as root returns the reward for the reward path formula for
* each state
*
* Has one Abstract path formula as sub formula/tree.
*
* @note
* This class is a hybrid of a state and path formula, and may only appear as the outermost operator.
* Hence, it is seen as neither a state nor a path formula, but is directly derived from AbstractFormula.
*
* @note
* This class does not contain a check() method like the other formula classes.
* The check method should only be called by the model checker to infer the correct check function for sub
* formulas. As this operator can only appear at the root, the method is not useful here.
* Use the checkRewardNoBoundOperator method from the DtmcPrctlModelChecker class instead.
*
* The subtree is seen as part of the object and deleted with it
* (this behavior can be prevented by setting them to NULL before deletion)
*
*
* @see AbstractStateFormula
* @see AbstractPathFormula
* @see ProbabilisticOperator
* @see ProbabilisticIntervalOperator
* @see AbstractPrctlFormula
*/
template <class T>
class RewardNoBoundOperator: public storm::property::abstract::RewardNoBoundOperator<T, AbstractPathFormula<T>>,
public storm::property::prctl::AbstractNoBoundOperator<T> {
public:
/*!
* Empty constructor
*/
RewardNoBoundOperator() {
// Intentionally left empty
}
/*!
* Constructor
*
* @param pathFormula The child node.
*/
RewardNoBoundOperator(AbstractPathFormula<T>* pathFormula)
: storm::property::abstract::RewardNoBoundOperator<T, AbstractPathFormula<T>>(pathFormula) {
// Intentionally left empty
}
/*!
* Constructor
*
* @param pathFormula The child node.
*/
RewardNoBoundOperator(AbstractPathFormula<T>* pathFormula, bool minimumOperator)
: storm::property::abstract::RewardNoBoundOperator<T, AbstractPathFormula<T>>(pathFormula, minimumOperator) {
// Intentionally left empty
}
virtual AbstractNoBoundOperator<T>* clone() const override {
RewardNoBoundOperator<T>* result = new RewardNoBoundOperator<T>();
if (this->pathFormulaIsSet()) {
result->setPathFormula(this->getPathFormula().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @note This function is not implemented in this class.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::prctl::AbstractModelChecker<T>& modelChecker, bool qualitative=false) const override {
return this->getPathFormula().check(modelChecker, qualitative);
}
};
} //namespace prctl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_PRCTL_REWARDNOBOUNDOPERATOR_H_ */

91
src/formula/Prctl/SteadyStateReward.h

@ -1,91 +0,0 @@
/*
* SteadyStateReward.h
*
* Created on: 08.04.2013
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_PRCTL_STEADYSTATEREWARD_H_
#define STORM_FORMULA_PRCTL_STEADYSTATEREWARD_H_
#include "AbstractPathFormula.h"
#include "AbstractStateFormula.h"
#include "src/formula/abstract/SteadyStateReward.h"
#include "src/formula/AbstractFormulaChecker.h"
#include <string>
namespace storm {
namespace property {
namespace prctl {
template <class T> class SteadyStateReward;
/*!
* @brief Interface class for model checkers that support SteadyStateReward.
*
* All model checkers that support the formula class SteadyStateReward must inherit
* this pure virtual class.
*/
template <class T>
class ISteadyStateRewardModelChecker {
public:
/*!
* @brief Evaluates CumulativeReward formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkSteadyStateReward(const SteadyStateReward<T>& obj, bool qualitative) const = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with a Steady State Reward node as root.
*
* @see AbstractPathFormula
* @see AbstractPrctlFormula
*/
template <class T>
class SteadyStateReward: public storm::property::abstract::SteadyStateReward<T>,
public AbstractPathFormula<T> {
public:
/*!
* Empty constructor
*/
SteadyStateReward() {
// Intentionally left empty
}
virtual ~SteadyStateReward() {
// Intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new SteadyState-object that is identical the called object.
*/
virtual AbstractPathFormula<T>* clone() const override {
return new SteadyStateReward<T>();
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::prctl::AbstractModelChecker<T>& modelChecker, bool qualitative) const override {
return modelChecker.template as<ISteadyStateRewardModelChecker>()->checkSteadyStateReward(*this, qualitative);
}
};
} //namespace prctl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_PRCTL_STEADYSTATEREWARD_H_ */

125
src/formula/Prctl/Until.h

@ -1,125 +0,0 @@
/*
* Until.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_PRCTL_UNTIL_H_
#define STORM_FORMULA_PRCTL_UNTIL_H_
#include "AbstractPathFormula.h"
#include "AbstractStateFormula.h"
#include "src/formula/abstract/Until.h"
#include "src/formula/AbstractFormulaChecker.h"
namespace storm {
namespace property {
namespace prctl {
template <class T> class Until;
/*!
* @brief Interface class for model checkers that support Until.
*
* All model checkers that support the formula class Until must inherit
* this pure virtual class.
*/
template <class T>
class IUntilModelChecker {
public:
/*!
* @brief Evaluates Until formula within a model checker.
*
* @param obj Formula object with subformulas.
* @return Result of the formula for every node.
*/
virtual std::vector<T> checkUntil(const Until<T>& obj, bool qualitative) const = 0;
};
/*!
* @brief
* Class for an abstract (path) formula tree with an Until node as root.
*
* Has two Abstract state formulas as sub formulas/trees.
*
* @par Semantics
* The formula holds iff eventually, formula \e right (the right subtree) holds, and before,
* \e left holds always.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractPathFormula
* @see AbstractPrctlFormula
*/
template <class T>
class Until : public storm::property::abstract::Until<T, AbstractStateFormula<T>>,
public AbstractPathFormula<T> {
public:
/*!
* Empty constructor
*/
Until() {
// Intentionally left empty
}
/*!
* Constructor
*
* @param left The left formula subtree
* @param right The left formula subtree
*/
Until(AbstractStateFormula<T>* left, AbstractStateFormula<T>* right)
: storm::property::abstract::Until<T, AbstractStateFormula<T>>(left, right) {
// Intentionally left empty
}
/*!
* Destructor.
*
* Also deletes the subtrees.
* (this behaviour can be prevented by setting the subtrees to NULL before deletion)
*/
virtual ~Until() {
// Intentionally left empty
}
/*!
* Clones the called object.
*
* Performs a "deep copy", i.e. the subtrees of the new object are clones of the original ones
*
* @returns a new BoundedUntil-object that is identical the called object.
*/
virtual AbstractPathFormula<T>* clone() const override {
Until<T>* result = new Until();
if (this->leftIsSet()) {
result->setLeft(this->getLeft().clone());
}
if (this->rightIsSet()) {
result->setRight(this->getRight().clone());
}
return result;
}
/*!
* Calls the model checker to check this formula.
* Needed to infer the correct type of formula class.
*
* @note This function should only be called in a generic check function of a model checker class. For other uses,
* the methods of the model checker should be used.
*
* @returns A vector indicating the probability that the formula holds for each state.
*/
virtual std::vector<T> check(const storm::modelchecker::prctl::AbstractModelChecker<T>& modelChecker, bool qualitative) const override {
return modelChecker.template as<IUntilModelChecker>()->checkUntil(*this, qualitative);
}
};
} //namespace prctl
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_PRCTL_UNTIL_H_ */

49
src/formula/PrctlFormulaChecker.h

@ -1,49 +0,0 @@
#ifndef STORM_FORMULA_PRCTLFORMULACHECKER_H_
#define STORM_FORMULA_PRCTLFORMULACHECKER_H_
#include "src/formula/AbstractFormulaChecker.h"
#include "src/formula/Prctl.h"
#include <iostream>
namespace storm {
namespace property {
/*!
* @brief Checks formulas if they are within PRCTL.
*
* This class implements AbstractFormulaChecker to check if a given formula
* is part of PRCTL logic.
*/
template <class T>
class PrctlFormulaChecker : public AbstractFormulaChecker<T> {
public:
/*!
* Implementation of AbstractFormulaChecker::validate() using code
* looking exactly like the sample code given there.
*/
virtual bool validate(const storm::property::abstract::AbstractFormula<T>* formula) const {
// What to support: Principles of Model Checking Def. 10.76 + syntactic sugar
if (
dynamic_cast<const storm::property::prctl::And<T>*>(formula) ||
dynamic_cast<const storm::property::prctl::Ap<T>*>(formula) ||
dynamic_cast<const storm::property::prctl::BoundedUntil<T>*>(formula) ||
dynamic_cast<const storm::property::prctl::Eventually<T>*>(formula) ||
dynamic_cast<const storm::property::prctl::Globally<T>*>(formula) ||
dynamic_cast<const storm::property::prctl::Next<T>*>(formula) ||
dynamic_cast<const storm::property::prctl::Not<T>*>(formula) ||
dynamic_cast<const storm::property::prctl::Or<T>*>(formula) ||
dynamic_cast<const storm::property::prctl::ProbabilisticNoBoundOperator<T>*>(formula) ||
dynamic_cast<const storm::property::prctl::ProbabilisticBoundOperator<T>*>(formula) ||
dynamic_cast<const storm::property::prctl::Until<T>*>(formula)
) {
return formula->validate(*this);
}
return false;
}
};
} // namespace property
} // namespace storm
#endif

92
src/formula/abstract/AbstractFormula.h

@ -1,92 +0,0 @@
/*
* Abstractformula.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_ABSTRACT_ABSTRACTFORMULA_H_
#define STORM_FORMULA_ABSTRACT_ABSTRACTFORMULA_H_
#include <string>
namespace storm {
namespace property {
namespace abstract {
template <class T> class AbstractFormula;
} //namespace abstract
} //namespace property
} //namespace storm
#include "src/formula/AbstractFormulaChecker.h"
namespace storm {
namespace property {
namespace abstract {
//abstract
/*!
* @brief Abstract base class for logic Abstract formulas in general.
*
* The namespace storm::property::abstract contains versions of the formula classes which are logic abstract, and contain
* the implementation which is not directly dependent on the logics.
* The classes for the subtrees are referenced by the template parameter FormulaType, which is typically instantiated in
* the derived classes of concrete logics.
*
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions "toString" and "validate"
* of the subformulas are needed.
*
* @note
* Even though the namespace is called "abstract", its classes may be completely implemented; abstract here denotes
* the abstraction from a concrete logic.
*
* @attention This class is abstract.
* @note Formula classes do not have copy constructors. The parameters of the constructors are usually the subtrees, so
* the syntax conflicts with copy constructors for unary operators. To produce an identical object, the classes
* AbstractFormula and AbstractFormula offer the method clone().
*
* This is the base class for every formula class in every logic.
*/
template <class T>
class AbstractFormula {
public:
/*!
* Virtual destructor.
*/
virtual ~AbstractFormula() {
// Intentionally left empty.
}
/*!
* @brief Return string representation of this formula.
*
* @note every subclass must implement this method.
*
* @returns a string representation of the formula
*/
virtual std::string toString() const = 0;
/*!
* @brief Checks if all subtrees are valid in some logic.
*
* @note Every subclass must implement this method.
*
* This method is given a checker object that knows which formula
* classes are allowed within the logic the checker represents. Every
* subclass is supposed to call checker.validate() for all child
* formulas and return true if and only if all those calls returned
* true.
*
* @param checker Checker object.
* @return true iff all subtrees are valid.
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const = 0;
};
} // namespace abstract
} // namespace property
} // namespace storm
#endif /* STORM_FORMULA_ABSTRACT_ABSTRACTFORMULA_H_ */

164
src/formula/abstract/And.h

@ -1,164 +0,0 @@
/*
* And.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_ABSTRACT_AND_H_
#define STORM_FORMULA_ABSTRACT_AND_H_
#include "src/formula/abstract/AbstractFormula.h"
#include "src/formula/AbstractFormulaChecker.h"
#include <string>
#include <type_traits>
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Logic-abstract Class for an abstract formula tree with AND node as root.
*
* Has two formulas as sub formulas/trees; the type is the template parameter FormulaType
*
* As AND is commutative, the order is \e theoretically not important, but will influence the order in which
* the model checker works.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractFormula
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "validate" of the subformulas are needed.
*/
template <class T, class FormulaType>
class And : public virtual AbstractFormula<T> {
// Throw a compiler error when FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::And<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/*!
* Empty constructor.
* Will create an AND-node without subnotes. Will not represent a complete formula!
*/
And() {
left = NULL;
right = NULL;
}
/*!
* Constructor.
* Creates an AND note with the parameters as subtrees.
*
* @param left The left sub formula
* @param right The right sub formula
*/
And(FormulaType* left, FormulaType* right) {
this->left = left;
this->right = right;
}
/*!
* Destructor.
*
* The subtrees are deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*/
virtual ~And() {
if (left != NULL) {
delete left;
}
if (right != NULL) {
delete right;
}
}
/*!
* Sets the left child node.
*
* @param newLeft the new left child.
*/
void setLeft(FormulaType* newLeft) {
left = newLeft;
}
/*!
* Sets the right child node.
*
* @param newRight the new right child.
*/
void setRight(FormulaType* newRight) {
right = newRight;
}
/*!
* @returns a pointer to the left child node
*/
const FormulaType& getLeft() const {
return *left;
}
/*!
* @returns a pointer to the right child node
*/
const FormulaType& getRight() const {
return *right;
}
/*!
*
* @return True if the left child is set, i.e. it does not point to nullptr; false otherwise
*/
bool leftIsSet() const {
return left != nullptr;
}
/*!
*
* @return True if the right child is set, i.e. it does not point to nullptr; false otherwise
*/
bool rightIsSet() const {
return right != nullptr;
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result = "(";
result += left->toString();
result += " & ";
result += right->toString();
result += ")";
return result;
}
/*!
* @brief Checks if all subtrees conform to some logic.
*
* @param checker Formula checker object.
* @return true iff all subtrees conform to some logic.
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const override {
return checker.validate(this->left) && checker.validate(this->right);
}
private:
FormulaType* left;
FormulaType* right;
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_AND_H_ */

84
src/formula/abstract/Ap.h

@ -1,84 +0,0 @@
/*
* Ap.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_ABSTRACT_AP_H_
#define STORM_FORMULA_ABSTRACT_AP_H_
#include "src/formula/abstract/AbstractFormula.h"
#include "src/formula/AbstractFormulaChecker.h"
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Logic-abstract Class for an abstract formula tree with atomic proposition as root.
*
* This class represents the leaves in the formula tree.
*
* @see AbstractFormula
*/
template <class T>
class Ap : public virtual AbstractFormula<T> {
public:
/*!
* Constructor
*
* Creates a new atomic proposition leaf, with the label Ap
*
* @param ap The string representing the atomic proposition
*/
Ap(std::string ap) {
this->ap = ap;
}
/*!
* Destructor.
* At this time, empty...
*/
virtual ~Ap() { }
/*!
* @returns the name of the atomic proposition
*/
const std::string& getAp() const {
return ap;
}
/*!
* @returns a string representation of the leaf.
*
*/
virtual std::string toString() const override {
return getAp();
}
/*!
* @brief Checks if all subtrees conform to some logic.
*
* As atomic propositions have no subformulas, we return true here.
*
* @param checker Formula checker object.
* @return true
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const override {
return true;
}
private:
std::string ap;
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_ABSTRCT_AP_H_ */

151
src/formula/abstract/BoundedEventually.h

@ -1,151 +0,0 @@
/*
* BoundedUntil.h
*
* Created on: 27.11.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_ABSTRACT_BOUNDEDEVENTUALLY_H_
#define STORM_FORMULA_ABSTRACT_BOUNDEDEVENTUALLY_H_
#include "src/formula/abstract/AbstractFormula.h"
#include "src/formula/AbstractFormulaChecker.h"
#include <cstdint>
#include <string>
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract (path) formula tree with a BoundedEventually node as root.
*
* Has one formula as sub formula/tree.
*
* @par Semantics
* The formula holds iff in at most \e bound steps, formula \e child holds.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "validate" of the subformulas are needed.
*
* @see AbstractFormula
*/
template <class T, class FormulaType>
class BoundedEventually : public virtual AbstractFormula<T> {
// Throw a compiler error when FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::BoundedEventually<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/*!
* Empty constructor
*/
BoundedEventually() {
this->child = nullptr;
bound = 0;
}
/*!
* Constructor
*
* @param child The child formula subtree
* @param bound The maximal number of steps
*/
BoundedEventually(FormulaType* child, uint_fast64_t bound) {
this->child = child;
this->bound = bound;
}
/*!
* Destructor.
*
* Also deletes the subtrees.
* (this behaviour can be prevented by setting the subtrees to NULL before deletion)
*/
virtual ~BoundedEventually() {
if (child != nullptr) {
delete child;
}
}
/*!
* @returns the child node
*/
const FormulaType& getChild() const {
return *child;
}
/*!
* Sets the subtree
* @param child the new child node
*/
void setChild(FormulaType* child) {
this->child = child;
}
/*!
*
* @return True if the child is set, i.e. it does not point to nullptr; false otherwise
*/
bool childIsSet() const {
return child != nullptr;
}
/*!
* @returns the maximally allowed number of steps for the bounded until operator
*/
uint_fast64_t getBound() const {
return bound;
}
/*!
* Sets the maximally allowed number of steps for the bounded until operator
*
* @param bound the new bound.
*/
void setBound(uint_fast64_t bound) {
this->bound = bound;
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result = "F<=";
result += std::to_string(bound);
result += " ";
result += child->toString();
return result;
}
/*!
* @brief Checks if the subtree conforms to some logic.
*
* @param checker Formula checker object.
* @return true iff the subtree conforms to some logic.
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const override {
return checker.validate(this->child);
}
private:
FormulaType* child;
uint_fast64_t bound;
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_BOUNDEDEVENTUALLY_H_ */

175
src/formula/abstract/BoundedNaryUntil.h

@ -1,175 +0,0 @@
/*
* BoundedNaryUntil.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_ABSTRACT_BOUNDEDNARYUNTIL_H_
#define STORM_FORMULA_ABSTRACT_BOUNDEDNARYUNTIL_H_
#include "src/formula/abstract/AbstractFormula.h"
#include <cstdint>
#include <string>
#include <vector>
#include <tuple>
#include <sstream>
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract (path) formula tree with a BoundedNaryUntil node as root.
*
* Has at least two formulas as sub formulas and an interval
* associated with all but the first sub formula. We'll call the first one
* \e left and all other one \e right.
*
* @par Semantics
* The formula holds iff \e left holds until eventually any of the \e right
* formulas holds after a number of steps contained in the interval
* associated with this formula.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "conforms" of the subformulas are needed.
*
* @see AbstractFormula
*/
template <class T, class FormulaType>
class BoundedNaryUntil : public virtual AbstractFormula<T> {
// Throw a compiler error when FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::BoundedNaryUntil<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/*!
* Empty constructor
*/
BoundedNaryUntil() {
this->left = nullptr;
this->right = new std::vector<std::tuple<FormulaType*,T,T>>();
}
/*!
* Constructor
*
* @param left The left formula subtree
* @param right The left formula subtree
*/
BoundedNaryUntil(FormulaType* left, std::vector<std::tuple<FormulaType*,T,T>>* right) {
this->left = left;
this->right = right;
}
/*!
* Destructor.
*
* Also deletes the subtrees.
* (this behaviour can be prevented by setting the subtrees to NULL before deletion)
*/
virtual ~BoundedNaryUntil() {
if (left != nullptr) {
delete left;
}
if (right != nullptr) {
delete right;
}
}
/*!
* Sets the left child node.
*
* @param newLeft the new left child.
*/
void setLeft(FormulaType* newLeft) {
left = newLeft;
}
void setRight(std::vector<std::tuple<FormulaType*,T,T>>* newRight) {
right = newRight;
}
/*!
*
* @return True if the left child is set, i.e. it does not point to nullptr; false otherwise
*/
bool leftIsSet() const {
return left != nullptr;
}
/*!
*
* @return True if the right child is set, i.e. it does not point to nullptr; false otherwise
*/
bool rightIsSet() const {
return right != nullptr;
}
/*!
* Sets the right child node.
*
* @param newRight the new right child.
*/
void addRight(FormulaType* newRight, T upperBound, T lowerBound) {
this->right->push_back(std::tuple<FormulaType*,T,T>(newRight, upperBound, lowerBound));
}
/*!
* @returns a pointer to the left child node
*/
const FormulaType& getLeft() const {
return *left;
}
/*!
* @returns a pointer to the right child nodes.
*/
const std::vector<std::tuple<FormulaType*,T,T>>& getRight() const {
return *right;
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::stringstream result;
result << "( " << left->toString();
for (auto it = this->right->begin(); it != this->right->end(); ++it) {
result << " U[" << std::get<1>(*it) << "," << std::get<2>(*it) << "] " << std::get<0>(*it)->toString();
}
result << ")";
return result.str();
}
/*!
* @brief Checks if all subtrees conform to some logic.
*
* @param checker Formula checker object.
* @return true iff all subtrees conform to some logic.
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const override {
bool res = checker.validate(this->left);
for (auto it = this->right->begin(); it != this->right->end(); ++it) {
res &= checker.validate(std::get<0>(*it));
}
return res;
}
private:
FormulaType* left;
std::vector<std::tuple<FormulaType*,T,T>>* right;
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_BOUNDEDNARYUNTIL_H_ */

182
src/formula/abstract/BoundedUntil.h

@ -1,182 +0,0 @@
/*
* BoundedUntil.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_ABSTRACT_BOUNDEDUNTIL_H_
#define STORM_FORMULA_ABSTRACT_BOUNDEDUNTIL_H_
#include "src/formula/abstract/AbstractFormula.h"
#include <cstdint>
#include <string>
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract (path) formula tree with a BoundedUntil node as root.
*
* Has two formulas as sub formulas/trees.
*
* @par Semantics
* The formula holds iff in at most \e bound steps, formula \e right (the right subtree) holds, and before,
* \e left holds.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "conforms" of the subformulas are needed.
*
* @see AbstractFormula
*/
template <class T, class FormulaType>
class BoundedUntil : public virtual AbstractFormula<T> {
// Throw a compiler error when FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::BoundedUntil<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/*!
* Empty constructor
*/
BoundedUntil() {
this->left = NULL;
this->right = NULL;
bound = 0;
}
/*!
* Constructor
*
* @param left The left formula subtree
* @param right The left formula subtree
* @param bound The maximal number of steps
*/
BoundedUntil(FormulaType* left, FormulaType* right,
uint_fast64_t bound) {
this->left = left;
this->right = right;
this->bound = bound;
}
/*!
* Destructor.
*
* Also deletes the subtrees.
* (this behaviour can be prevented by setting the subtrees to NULL before deletion)
*/
virtual ~BoundedUntil() {
if (left != NULL) {
delete left;
}
if (right != NULL) {
delete right;
}
}
/*!
* Sets the left child node.
*
* @param newLeft the new left child.
*/
void setLeft(FormulaType* newLeft) {
left = newLeft;
}
/*!
* Sets the right child node.
*
* @param newRight the new right child.
*/
void setRight(FormulaType* newRight) {
right = newRight;
}
/*!
* @returns a pointer to the left child node
*/
const FormulaType& getLeft() const {
return *left;
}
/*!
* @returns a pointer to the right child node
*/
const FormulaType& getRight() const {
return *right;
}
/*!
*
* @return True if the left child is set, i.e. it does not point to nullptr; false otherwise
*/
bool leftIsSet() const {
return left != nullptr;
}
/*!
*
* @return True if the right child is set, i.e. it does not point to nullptr; false otherwise
*/
bool rightIsSet() const {
return right != nullptr;
}
/*!
* @returns the maximally allowed number of steps for the bounded until operator
*/
uint_fast64_t getBound() const {
return bound;
}
/*!
* Sets the maximally allowed number of steps for the bounded until operator
*
* @param bound the new bound.
*/
void setBound(uint_fast64_t bound) {
this->bound = bound;
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result = left->toString();
result += " U<=";
result += std::to_string(bound);
result += " ";
result += right->toString();
return result;
}
/*!
* @brief Checks if all subtrees conform to some logic.
*
* @param checker Formula checker object.
* @return true iff all subtrees conform to some logic.
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const override {
return checker.validate(this->left) && checker.validate(this->right);
}
private:
FormulaType* left;
FormulaType* right;
uint_fast64_t bound;
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_BOUNDEDUNTIL_H_ */

101
src/formula/abstract/CumulativeReward.h

@ -1,101 +0,0 @@
/*
* InstantaneousReward.h
*
* Created on: 26.12.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_ABSTRACT_CUMULATIVEREWARD_H_
#define STORM_FORMULA_ABSTRACT_CUMULATIVEREWARD_H_
#include "AbstractFormula.h"
#include "src/formula/AbstractFormulaChecker.h"
#include <string>
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract (path) formula tree with a Cumulative Reward node as root.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractPathFormula
* @see AbstractFormula
*/
template <class T>
class CumulativeReward : public virtual AbstractFormula<T> {
public:
/*!
* Empty constructor
*/
CumulativeReward() {
bound = 0;
}
/*!
* Constructor
*
* @param bound The time bound of the reward formula
*/
CumulativeReward(T bound) {
this->bound = bound;
}
/*!
* Empty destructor.
*/
virtual ~CumulativeReward() {
// Intentionally left empty.
}
/*!
* @returns the time instance for the instantaneous reward operator
*/
T getBound() const {
return bound;
}
/*!
* Sets the the time instance for the instantaneous reward operator
*
* @param bound the new bound.
*/
void setBound(T bound) {
this->bound = bound;
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result = "C <= ";
result += std::to_string(bound);
return result;
}
/*!
* @brief Checks if all subtrees conform to some logic.
*
* As CumulativeReward objects have no subformulas, we return true here.
*
* @param checker Formula checker object.
* @return true
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const override {
return true;
}
private:
T bound;
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_INSTANTANEOUSREWARD_H_ */

125
src/formula/abstract/Eventually.h

@ -1,125 +0,0 @@
/*
* Next.h
*
* Created on: 26.12.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_ABSTRACT_EVENTUALLY_H_
#define STORM_FORMULA_ABSTRACT_EVENTUALLY_H_
#include "src/formula/abstract/AbstractFormula.h"
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract (path) formula tree with an Eventually node as root.
*
* Has one formula as sub formula/tree.
*
* @par Semantics
* The formula holds iff eventually \e child holds.
*
* The subtree is seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to nullptr before deletion)
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "conforms" of the subformulas are needed.
*
* @see AbstractFormula
*/
template <class T, class FormulaType>
class Eventually : public virtual AbstractFormula<T> {
// Throw a compiler error when FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::Eventually<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/*!
* Empty constructor
*/
Eventually() {
this->child = nullptr;
}
/*!
* Constructor
*
* @param child The child node
*/
Eventually(FormulaType* child) {
this->child = child;
}
/*!
* Constructor.
*
* Also deletes the subtree.
* (this behaviour can be prevented by setting the subtrees to nullptr before deletion)
*/
virtual ~Eventually() {
if (child != nullptr) {
delete child;
}
}
/*!
* @returns the child node
*/
const FormulaType& getChild() const {
return *child;
}
/*!
* Sets the subtree
* @param child the new child node
*/
void setChild(FormulaType* child) {
this->child = child;
}
/*!
*
* @return True if the child node is set, i.e. it does not point to nullptr; false otherwise
*/
bool childIsSet() const {
return child != nullptr;
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result = "F ";
result += child->toString();
return result;
}
/*!
* @brief Checks if the subtree conforms to some logic.
*
* @param checker Formula checker object.
* @return true iff the subtree conforms to some logic.
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const override {
return checker.validate(this->child);
}
private:
FormulaType* child;
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_EVENTUALLY_H_ */

126
src/formula/abstract/Globally.h

@ -1,126 +0,0 @@
/*
* Next.h
*
* Created on: 26.12.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_ABSTRACT_GLOBALLY_H_
#define STORM_FORMULA_ABSTRACT_GLOBALLY_H_
#include "src/formula/abstract/AbstractFormula.h"
#include "src/formula/AbstractFormulaChecker.h"
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract formula tree with a Globally node as root.
*
* Has one formula as sub formula/tree.
*
* @par Semantics
* The formula holds iff globally \e child holds.
*
* The subtree is seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to nullptr before deletion)
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "conforms" of the subformulas are needed.
*
* @see AbstractFormula
*/
template <class T, class FormulaType>
class Globally : public virtual AbstractFormula<T> {
// Throw a compiler error when FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::Globally<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/*!
* Empty constructor
*/
Globally() {
this->child = nullptr;
}
/*!
* Constructor
*
* @param child The child node
*/
Globally(FormulaType* child) {
this->child = child;
}
/*!
* Constructor.
*
* Also deletes the subtree.
* (this behaviour can be prevented by setting the subtrees to nullptr before deletion)
*/
virtual ~Globally() {
if (child != nullptr) {
delete child;
}
}
/*!
* @returns the child node
*/
const FormulaType& getChild() const {
return *child;
}
/*!
* Sets the subtree
* @param child the new child node
*/
void setChild(FormulaType* child) {
this->child = child;
}
/*!
*
* @return True if the child node is set, i.e. it does not point to nullptr; false otherwise
*/
bool childIsSet() const {
return child != nullptr;
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result = "G ";
result += child->toString();
return result;
}
/*!
* @brief Checks if the subtree conforms to some logic.
*
* @param checker Formula checker object.
* @return true iff the subtree conforms to some logic.
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const override {
return checker.validate(this->child);
}
private:
FormulaType* child;
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_GLOBALLY_H_ */

41
src/formula/abstract/IOptimizingOperator.h

@ -1,41 +0,0 @@
/*
* IOptimizingOperator.h
*
* Created on: 17.04.2013
* Author: thomas
*/
#ifndef STORM_FORMULA_ABSTRACT_IOPTIMIZINGOPERATOR_H_
#define STORM_FORMULA_ABSTRACT_IOPTIMIZINGOPERATOR_H_
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief Interface for optimizing operators
*
* Needed to link abstract classes in concrete logics with the logic-abstract implementation.
*/
class IOptimizingOperator {
public:
/*!
* Retrieves whether the operator is to be interpreted as an optimizing (i.e. min/max) operator.
* @returns True if the operator is an optimizing operator.
*/
virtual bool isOptimalityOperator() const = 0;
/*!
* Retrieves whether the operator is a minimizing operator given that it is an optimality
* operator.
* @returns True if the operator is an optimizing operator and it is a minimizing operator and
* false otherwise, i.e. if it is either not an optimizing operator or not a minimizing operator.
*/
virtual bool isMinimumOperator() const = 0;
};
} /* namespace abstract */
} /* namespace property */
} /* namespace storm */
#endif /* IOPTIMIZINGOPERATOR_H_ */

101
src/formula/abstract/InstantaneousReward.h

@ -1,101 +0,0 @@
/*
* InstantaneousReward.h
*
* Created on: 26.12.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_ABSTRACT_INSTANTANEOUSREWARD_H_
#define STORM_FORMULA_ABSTRACT_INSTANTANEOUSREWARD_H_
#include "AbstractFormula.h"
#include "src/formula/AbstractFormulaChecker.h"
#include <cstdint>
#include <string>
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract (path) formula tree with a Instantaneous Reward node as root.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractFormula
*/
template <class T>
class InstantaneousReward : public virtual AbstractFormula<T> {
public:
/*!
* Empty constructor
*/
InstantaneousReward() {
bound = 0;
}
/*!
* Constructor
*
* @param bound The time instance of the reward formula
*/
InstantaneousReward(uint_fast64_t bound) {
this->bound = bound;
}
/*!
* Empty destructor.
*/
virtual ~InstantaneousReward() {
// Intentionally left empty.
}
/*!
* @returns the time instance for the instantaneous reward operator
*/
uint_fast64_t getBound() const {
return bound;
}
/*!
* Sets the the time instance for the instantaneous reward operator
*
* @param bound the new bound.
*/
void setBound(uint_fast64_t bound) {
this->bound = bound;
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result = "I=";
result += std::to_string(bound);
return result;
}
/*!
* @brief Checks if all subtrees conform to some logic.
*
* As InstantaneousReward formulas have no subformulas, we return true here.
*
* @param checker Formula checker object.
* @return true
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const override {
return true;
}
private:
uint_fast64_t bound;
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_INSTANTANEOUSREWARD_H_ */

128
src/formula/abstract/Next.h

@ -1,128 +0,0 @@
/*
* Next.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_ABSTRACT_NEXT_H_
#define STORM_FORMULA_ABSTRACT_NEXT_H_
#include "src/formula/abstract/AbstractFormula.h"
#include "src/formula/AbstractFormulaChecker.h"
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract (path) formula tree with a Next node as root.
*
* Has two formulas as sub formulas/trees.
*
* @par Semantics
* The formula holds iff in the next step, \e child holds
*
* The subtree is seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "conforms" of the subformulas are needed.
*
* @see AbstractFormula
*/
template <class T, class FormulaType>
class Next : public virtual AbstractFormula<T> {
// Throw a compiler error when FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::Next<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/*!
* Empty constructor
*/
Next() {
this->child = NULL;
}
/*!
* Constructor
*
* @param child The child node
*/
Next(FormulaType* child) {
this->child = child;
}
/*!
* Constructor.
*
* Also deletes the subtree.
* (this behaviour can be prevented by setting the subtrees to NULL before deletion)
*/
virtual ~Next() {
if (child != NULL) {
delete child;
}
}
/*!
* @returns the child node
*/
const FormulaType& getChild() const {
return *child;
}
/*!
* Sets the subtree
* @param child the new child node
*/
void setChild(FormulaType* child) {
this->child = child;
}
/*!
*
* @return True if the child node is set, i.e. it does not point to nullptr; false otherwise
*/
bool childIsSet() const {
return child != nullptr;
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result = "(";
result += " X ";
result += child->toString();
result += ")";
return result;
}
/*!
* @brief Checks if the subtree conforms to some logic.
*
* @param checker Formula checker object.
* @return true iff the subtree conforms to some logic.
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const override {
return checker.validate(this->child);
}
private:
FormulaType* child;
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_NEXT_H_ */

122
src/formula/abstract/Not.h

@ -1,122 +0,0 @@
/*
* Not.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_ABSTRACT_NOT_H_
#define STORM_FORMULA_ABSTRACT_NOT_H_
#include "src/formula/abstract/AbstractFormula.h"
#include "src/formula/AbstractFormulaChecker.h"
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract formula tree with NOT node as root.
*
* Has one formula as sub formula/tree.
*
* The subtree is seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "conforms" of the subformulas are needed.
*
* @see AbstractFormula
*/
template <class T, class FormulaType>
class Not : public virtual AbstractFormula<T> {
// Throw a compiler error if FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::Not<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/*!
* Empty constructor
*/
Not() {
this->child = NULL;
}
/*!
* Constructor
* @param child The child node
*/
Not(FormulaType* child) {
this->child = child;
}
/*!
* Destructor
*
* Also deletes the subtree
* (this behavior can be prevented by setting them to NULL before deletion)
*/
virtual ~Not() {
if (child != NULL) {
delete child;
}
}
/*!
* @returns The child node
*/
const FormulaType& getChild() const {
return *child;
}
/*!
* Sets the subtree
* @param child the new child node
*/
void setChild(FormulaType* child) {
this->child = child;
}
/*!
*
* @return True if the child node is set, i.e. it does not point to nullptr; false otherwise
*/
bool childIsSet() const {
return child != nullptr;
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result = "!";
result += child->toString();
return result;
}
/*!
* @brief Checks if the subtree conforms to some logic.
*
* @param checker Formula checker object.
* @return true iff the subtree conforms to some logic.
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const override {
return checker.validate(this->child);
}
private:
FormulaType* child;
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_NOT_H_ */

72
src/formula/abstract/OptimizingOperator.h

@ -1,72 +0,0 @@
#ifndef STORM_FORMULA_ABSTRACT_OPTIMIZINGOPERATOR_H_
#define STORM_FORMULA_ABSTRACT_OPTIMIZINGOPERATOR_H_
#include "IOptimizingOperator.h"
namespace storm {
namespace property {
namespace abstract {
/*!
*
*/
class OptimizingOperator : public virtual IOptimizingOperator {
public:
/*!
* Empty constructor
*/
OptimizingOperator() : optimalityOperator(false), minimumOperator(false) {
}
/*!
* Constructor
*
* @param minimumOperator A flag indicating whether this operator is a minimizing or a maximizing operator.
*/
OptimizingOperator(bool minimumOperator) : optimalityOperator(true), minimumOperator(minimumOperator) {
}
/*!
* Destructor
*/
virtual ~OptimizingOperator() {
// Intentionally left empty
}
/*!
* Retrieves whether the operator is to be interpreted as an optimizing (i.e. min/max) operator.
* @returns True if the operator is an optimizing operator.
*/
virtual bool isOptimalityOperator() const {
return optimalityOperator;
}
/*!
* Retrieves whether the operator is a minimizing operator given that it is an optimality
* operator.
* @returns True if the operator is an optimizing operator and it is a minimizing operator and
* false otherwise, i.e. if it is either not an optimizing operator or not a minimizing operator.
*/
virtual bool isMinimumOperator() const {
return optimalityOperator && minimumOperator;
}
private:
// A flag that indicates whether this operator is meant as an optimizing (i.e. min/max) operator
// over a nondeterministic model.
bool optimalityOperator;
// In the case this operator is an optimizing operator, this flag indicates whether it is
// looking for the minimum or the maximum value.
bool minimumOperator;
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_OPTIMIZINGOPERATOR_H_ */

161
src/formula/abstract/Or.h

@ -1,161 +0,0 @@
/*
* Or.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_ABSTRACT_OR_H_
#define STORM_FORMULA_ABSTRACT_OR_H_
#include "src/formula/abstract/AbstractFormula.h"
#include "src/formula/AbstractFormulaChecker.h"
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract formula tree with OR node as root.
*
* Has two formulas as sub formulas/trees.
*
* As OR is commutative, the order is \e theoretically not important, but will influence the order in which
* the model checker works.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "conforms" of the subformulas are needed.
*
* @see AbstractFormula
*/
template <class T, class FormulaType>
class Or : public virtual AbstractFormula<T> {
// Throw a compiler error if FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::Or<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/*!
* Empty constructor.
* Will create an AND-node without subnotes. Will not represent a complete formula!
*/
Or() {
left = NULL;
right = NULL;
}
/*!
* Constructor.
* Creates an AND note with the parameters as subtrees.
*
* @param left The left sub formula
* @param right The right sub formula
*/
Or(FormulaType* left, FormulaType* right) {
this->left = left;
this->right = right;
}
/*!
* Destructor.
*
* The subtrees are deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*/
virtual ~Or() {
if (left != NULL) {
delete left;
}
if (right != NULL) {
delete right;
}
}
/*!
* Sets the left child node.
*
* @param newLeft the new left child.
*/
void setLeft(FormulaType* newLeft) {
left = newLeft;
}
/*!
* Sets the right child node.
*
* @param newRight the new right child.
*/
void setRight(FormulaType* newRight) {
right = newRight;
}
/*!
* @returns a pointer to the left child node
*/
const FormulaType& getLeft() const {
return *left;
}
/*!
* @returns a pointer to the right child node
*/
const FormulaType& getRight() const {
return *right;
}
/*!
*
* @return True if the left child is set, i.e. it does not point to nullptr; false otherwise
*/
bool leftIsSet() const {
return left != nullptr;
}
/*!
*
* @return True if the right child is set, i.e. it does not point to nullptr; false otherwise
*/
bool rightIsSet() const {
return right != nullptr;
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result = "(";
result += left->toString();
result += " | ";
result += right->toString();
result += ")";
return result;
}
/*!
* @brief Checks if all subtrees conform to some logic.
*
* @param checker Formula checker object.
* @return true iff all subtrees conform to some logic.
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const override {
return checker.validate(this->left) && checker.validate(this->right);
}
private:
FormulaType* left;
FormulaType* right;
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_OR_H_ */

194
src/formula/abstract/PathBoundOperator.h

@ -1,194 +0,0 @@
/*
* PathBoundOperator.h
*
* Created on: 27.12.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_ABSTRACT_PATHBOUNDOPERATOR_H_
#define STORM_FORMULA_ABSTRACT_PATHBOUNDOPERATOR_H_
#include "src/formula/abstract/AbstractFormula.h"
#include "src/formula/abstract/AbstractFormula.h"
#include "src/formula/AbstractFormulaChecker.h"
#include "src/formula/ComparisonType.h"
#include "src/formula/abstract/OptimizingOperator.h"
#include "src/utility/constants.h"
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract formula tree with a P (probablistic) operator node over a probability interval
* as root.
*
* Has one formula as sub formula/tree.
*
* @par Semantics
* The formula holds iff the probability that the path formula holds is inside the bounds
* specified in this operator
*
* The subtree is seen as part of the object and deleted with it
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "conforms" of the subformulas are needed.
*
* @see AbstractFormula
* @see PathNoBoundOperator
*/
template<class T, class FormulaType>
class PathBoundOperator : public virtual AbstractFormula<T>, public OptimizingOperator {
// Throw a compiler error if FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::PathBoundOperator<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/*!
* Constructor for non-optimizing operator.
*
* @param comparisonOperator The relation for the bound.
* @param bound The bound for the probability
* @param pathFormula The child node
*/
PathBoundOperator(storm::property::ComparisonType comparisonOperator, T bound, FormulaType* pathFormula)
: comparisonOperator(comparisonOperator), bound(bound), pathFormula(pathFormula) {
// Intentionally left empty
}
/*!
* Constructor for optimizing operator.
*
* @param comparisonOperator The relation for the bound.
* @param bound The bound for the probability
* @param pathFormula The child node
* @param minimumOperator Indicator, if operator should be minimum or maximum operator.
*/
PathBoundOperator(storm::property::ComparisonType comparisonOperator, T bound, FormulaType* pathFormula, bool minimumOperator)
: OptimizingOperator(minimumOperator), comparisonOperator(comparisonOperator), bound(bound), pathFormula(pathFormula) {
// Intentionally left empty
}
/*!
* Destructor
*
* The subtree is deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*/
virtual ~PathBoundOperator() {
if (pathFormula != nullptr) {
delete pathFormula;
}
}
/*!
* @returns the child node (representation of a formula)
*/
const FormulaType& getPathFormula () const {
return *pathFormula;
}
/*!
* Sets the child node
*
* @param pathFormula the path formula that becomes the new child node
*/
void setPathFormula(FormulaType* pathFormula) {
this->pathFormula = pathFormula;
}
/*!
*
* @return True if the path formula is set, i.e. it does not point to nullptr; false otherwise
*/
bool pathFormulaIsSet() const {
return pathFormula != nullptr;
}
/*!
* @returns the comparison relation
*/
const storm::property::ComparisonType getComparisonOperator() const {
return comparisonOperator;
}
void setComparisonOperator(storm::property::ComparisonType comparisonOperator) {
this->comparisonOperator = comparisonOperator;
}
/*!
* @returns the bound for the measure
*/
const T& getBound() const {
return bound;
}
/*!
* Sets the interval in which the probability that the path formula holds may lie in.
*
* @param bound The bound for the measure
*/
void setBound(T bound) {
this->bound = bound;
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result = "";
switch (comparisonOperator) {
case LESS: result += "<"; break;
case LESS_EQUAL: result += "<="; break;
case GREATER: result += ">"; break;
case GREATER_EQUAL: result += ">="; break;
}
result += " ";
result += std::to_string(bound);
result += " [";
result += pathFormula->toString();
result += "]";
return result;
}
bool meetsBound(T value) const {
switch (comparisonOperator) {
case LESS: return value < bound; break;
case LESS_EQUAL: return value <= bound; break;
case GREATER: return value > bound; break;
case GREATER_EQUAL: return value >= bound; break;
default: return false;
}
}
/*!
* @brief Checks if the subtree conforms to some logic.
*
* @param checker Formula checker object.
* @return true iff the subtree conforms to some logic.
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const override {
return checker.validate(this->pathFormula);
}
private:
storm::property::ComparisonType comparisonOperator;
T bound;
FormulaType* pathFormula;
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_PATHBOUNDOPERATOR_H_ */

160
src/formula/abstract/PathNoBoundOperator.h

@ -1,160 +0,0 @@
/*
* PathNoBoundOperator.h
*
* Created on: 27.12.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_ABSTRACT_NOBOUNDOPERATOR_H_
#define STORM_FORMULA_ABSTRACT_NOBOUNDOPERATOR_H_
#include "src/formula/abstract/AbstractFormula.h"
#include "src/formula/AbstractFormulaChecker.h"
#include "src/formula/abstract/OptimizingOperator.h"
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract formula tree with a P (probablistic) operator without declaration of probabilities
* as root.
*
* Checking a formula with this operator as root returns the probabilities that the path formula holds
* (for each state)
*
* Has one formula as sub formula/tree.
*
* @note
* This class is a hybrid of a state and path formula, and may only appear as the outermost operator.
* Hence, it is seen as neither a state nor a path formula, but is directly derived from AbstractFormula.
*
* @note
* This class does not contain a check() method like the other formula classes.
* The check method should only be called by the model checker to infer the correct check function for sub
* formulas. As this operator can only appear at the root, the method is not useful here.
* Use the checkProbabilisticNoBoundOperator method from the DtmcPrctlModelChecker class instead.
*
* The subtree is seen as part of the object and deleted with it
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "conforms" of the subformulas are needed.
*
* @see AbstractFormula
* @see PathBoundOperator
*/
template <class T, class FormulaType>
class PathNoBoundOperator: public virtual AbstractFormula<T>, public OptimizingOperator {
// Throw a compiler error if FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::PathNoBoundOperator<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/*!
* Empty constructor
*/
PathNoBoundOperator() :
OptimizingOperator(false) {
this->pathFormula = nullptr;
}
/*!
* Constructor
*
* @param pathFormula The child node.
*/
PathNoBoundOperator(FormulaType* pathFormula) {
this->pathFormula = pathFormula;
}
/*!
* Constructor
*
* @param pathFormula The child node.
* @param minimumOperator A flag indicating whether this operator is a minimizing or a
* maximizing operator.
*/
PathNoBoundOperator(FormulaType* pathFormula, bool minimumOperator)
: OptimizingOperator(minimumOperator) {
this->pathFormula = pathFormula;
}
/*!
* Destructor
*/
virtual ~PathNoBoundOperator() {
if (pathFormula != NULL) {
delete pathFormula;
}
}
/*!
* @returns the child node (representation of an abstract path formula)
*/
const FormulaType& getPathFormula () const {
return *pathFormula;
}
/*!
* Sets the child node
*
* @param pathFormula the path formula that becomes the new child node
*/
void setPathFormula(FormulaType* pathFormula) {
this->pathFormula = pathFormula;
}
/*!
*
* @return True if the path formula is set, i.e. it does not point to nullptr; false otherwise
*/
bool pathFormulaIsSet() const {
return pathFormula != nullptr;
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result;
if (this->isOptimalityOperator()) {
if (this->isMinimumOperator()) {
result += "min";
} else {
result += "max";
}
}
result += " = ? [";
result += this->getPathFormula().toString();
result += "]";
return result;
}
/*!
* @brief Checks if the subtree conforms to some logic.
*
* @param checker Formula checker object.
* @return true iff the subtree conforms to some logic.
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const override {
return checker.validate(this->pathFormula);
}
private:
FormulaType* pathFormula;
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_NOBOUNDOPERATOR_H_ */

114
src/formula/abstract/ProbabilisticBoundOperator.h

@ -1,114 +0,0 @@
/*
* ProbabilisticBoundOperator.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_ABSTRACT_PROBABILISTICBOUNDOPERATOR_H_
#define STORM_FORMULA_ABSTRACT_PROBABILISTICBOUNDOPERATOR_H_
#include "src/formula/abstract/AbstractFormula.h"
#include "src/formula/abstract/PathBoundOperator.h"
#include "src/formula/abstract/OptimizingOperator.h"
#include "utility/constants.h"
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract formula tree with a P (probablistic) operator node over a probability interval
* as root.
*
* Has one Abstract path formula as sub formula/tree.
*
* @par Semantics
* The formula holds iff the probability that the path formula holds is inside the bounds
* specified in this operator
*
* The subtree is seen as part of the object and deleted with it
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "conforms" of the subformulas are needed.
*
* @see AbstractFormula
* @see AbstractFormula
* @see ProbabilisticOperator
* @see ProbabilisticNoBoundsOperator
* @see AbstractFormula
*/
template<class T, class FormulaType>
class ProbabilisticBoundOperator : public PathBoundOperator<T, FormulaType> {
// Throw a compiler error if FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::ProbabilisticBoundOperator<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/*!
* Empty constructor
*/
ProbabilisticBoundOperator() : PathBoundOperator<T, FormulaType>
(LESS_EQUAL, storm::utility::constantZero<T>(), nullptr) {
// Intentionally left empty
}
/*!
* Constructor
*
* @param comparisonRelation The relation to compare the actual value and the bound
* @param bound The bound for the probability
* @param pathFormula The child node
*/
ProbabilisticBoundOperator(
storm::property::ComparisonType comparisonRelation,
T bound,
FormulaType* pathFormula)
: PathBoundOperator<T, FormulaType>(comparisonRelation, bound, pathFormula) {
// Intentionally left empty
}
/*!
* Constructor
*
* @param comparisonRelation
* @param bound
* @param pathFormula
* @param minimumOperator
*/
ProbabilisticBoundOperator(
storm::property::ComparisonType comparisonRelation,
T bound,
FormulaType* pathFormula,
bool minimumOperator)
: PathBoundOperator<T, FormulaType>(comparisonRelation, bound, pathFormula, minimumOperator){
// Intentionally left empty
}
/*!
* Destructor
*/
virtual ~ProbabilisticBoundOperator() {
// Intentionally left empty
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result = "P ";
result += PathBoundOperator<T, FormulaType>::toString();
return result;
}
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_PROBABILISTICBOUNDOPERATOR_H_ */

104
src/formula/abstract/ProbabilisticNoBoundOperator.h

@ -1,104 +0,0 @@
/*
* ProbabilisticNoBoundOperator.h
*
* Created on: 12.12.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_ABSTRACT_PROBABILISTICNOBOUNDOPERATOR_H_
#define STORM_FORMULA_ABSTRACT_PROBABILISTICNOBOUNDOPERATOR_H_
#include "AbstractFormula.h"
#include "src/formula/abstract/AbstractFormula.h"
#include "PathNoBoundOperator.h"
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract formula tree with a P (probablistic) operator without declaration of probabilities
* as root.
*
* Checking a formula with this operator as root returns the probabilities that the path formula holds
* (for each state)
*
* Has one Abstract path formula as sub formula/tree.
*
* @note
* This class is a hybrid of a state and path formula, and may only appear as the outermost operator.
* Hence, it is seen as neither a state nor a path formula, but is directly derived from AbstractFormula.
*
* @note
* This class does not contain a check() method like the other formula classes.
* The check method should only be called by the model checker to infer the correct check function for sub
* formulas. As this operator can only appear at the root, the method is not useful here.
* Use the checkProbabilisticNoBoundOperator method from the DtmcPrctlModelChecker class instead.
*
* The subtree is seen as part of the object and deleted with it
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "conforms" of the subformulas are needed.
*
* @see AbstractFormula
* @see PathNoBoundOperator
* @see ProbabilisticBoundOperator
*/
template <class T, class FormulaType>
class ProbabilisticNoBoundOperator: public PathNoBoundOperator<T, FormulaType> {
// Throw a compiler error if FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::ProbabilisticNoBoundOperator<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/*!
* Empty constructor
*/
ProbabilisticNoBoundOperator() : PathNoBoundOperator<T, FormulaType>(nullptr) {
// Intentionally left empty
}
/*!
* Constructor
*
* @param pathFormula The child node.
*/
ProbabilisticNoBoundOperator(FormulaType* pathFormula) : PathNoBoundOperator<T, FormulaType>(pathFormula) {
// Intentionally left empty
}
/*!
* Destructor
*/
virtual ~ProbabilisticNoBoundOperator() {
// Intentionally left empty
}
/*!
* Constructor
*
* @param pathFormula The child node.
*/
ProbabilisticNoBoundOperator(FormulaType* pathFormula, bool minimumOperator) : PathNoBoundOperator<T, FormulaType>(pathFormula, minimumOperator) {
// Intentionally left empty
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result = "P";
result += PathNoBoundOperator<T, FormulaType>::toString();
return result;
}
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_PROBABILISTICNOBOUNDOPERATOR_H_ */

106
src/formula/abstract/RewardBoundOperator.h

@ -1,106 +0,0 @@
/*
* RewardBoundOperator.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_ABSTRACT_REWARDBOUNDOPERATOR_H_
#define STORM_FORMULA_ABSTRACT_REWARDBOUNDOPERATOR_H_
#include "PathBoundOperator.h"
#include "utility/constants.h"
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract formula tree with a R (reward) operator node over a reward interval as root.
*
* Has a reward path formula as sub formula/tree.
*
* @par Semantics
* The formula holds iff the reward of the reward path formula is inside the bounds
* specified in this operator
*
* The subtree is seen as part of the object and deleted with it
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "conforms" of the subformulas are needed.
*
* @see AbstractFormula
* @see PathBoundOperator
* @see RewardNoBoundOperator
*/
template<class T, class FormulaType>
class RewardBoundOperator : public PathBoundOperator<T, FormulaType> {
// Throw a compiler error if FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::RewardBoundOperator<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/*!
* Empty constructor
*/
RewardBoundOperator() : PathBoundOperator<T, FormulaType>(LESS_EQUAL, storm::utility::constantZero<T>(), nullptr) {
// Intentionally left empty
}
/*!
* Constructor
*
* @param comparisonRelation The relation to compare the actual value and the bound
* @param bound The bound for the probability
* @param pathFormula The child node
*/
RewardBoundOperator(
storm::property::ComparisonType comparisonRelation,
T bound,
FormulaType* pathFormula) :
PathBoundOperator<T, FormulaType>(comparisonRelation, bound, pathFormula) {
// Intentionally left empty
}
/*!
* Constructor
* @param comparisonRelation
* @param bound
* @param pathFormula
* @param minimumOperator
*/
RewardBoundOperator(
storm::property::ComparisonType comparisonRelation,
T bound,
FormulaType* pathFormula,
bool minimumOperator)
: PathBoundOperator<T, FormulaType>(comparisonRelation, bound, pathFormula, minimumOperator) {
// Intentionally left empty
}
/*!
* Destructor
*/
virtual ~RewardBoundOperator() {
// Intentionally left empty
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result = "R ";
result += PathBoundOperator<T, FormulaType>::toString();
return result;
}
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_REWARDBOUNDOPERATOR_H_ */

103
src/formula/abstract/RewardNoBoundOperator.h

@ -1,103 +0,0 @@
/*
* RewardNoBoundOperator.h
*
* Created on: 25.12.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_ABSTRACT_REWARDNOBOUNDOPERATOR_H_
#define STORM_FORMULA_ABSTRACT_REWARDNOBOUNDOPERATOR_H_
#include "AbstractFormula.h"
#include "PathNoBoundOperator.h"
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract formula tree with a R (reward) operator without declaration of reward values
* as root.
*
* Checking a formula with this operator as root returns the reward for the reward path formula for
* each state
*
* Has one formula as sub formula/tree.
*
* @note
* This class is a hybrid of a state and path formula, and may only appear as the outermost operator.
* Hence, it is seen as neither a state nor a path formula, but is directly derived from AbstractFormula.
*
* @note
* This class does not contain a check() method like the other formula classes.
* The check method should only be called by the model checker to infer the correct check function for sub
* formulas. As this operator can only appear at the root, the method is not useful here.
* Use the checkRewardNoBoundOperator method from the DtmcPrctlModelChecker class instead.
*
* The subtree is seen as part of the object and deleted with it
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "conforms" of the subformulas are needed.
*
* @see AbstractFormula
* @see PathNoBoundOperator
* @see RewardBoundOperator
*/
template <class T, class FormulaType>
class RewardNoBoundOperator: public PathNoBoundOperator<T, FormulaType> {
// Throw a compiler error if FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::RewardNoBoundOperator<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/*!
* Empty constructor
*/
RewardNoBoundOperator() : PathNoBoundOperator<T, FormulaType>(nullptr) {
// Intentionally left empty
}
/*!
* Constructor
*
* @param pathFormula The child node.
*/
RewardNoBoundOperator(FormulaType* pathFormula) : PathNoBoundOperator<T, FormulaType>(pathFormula) {
// Intentionally left empty
}
/*!
* Constructor
*
* @param pathFormula The child node.
*/
RewardNoBoundOperator(FormulaType* pathFormula, bool minimumOperator) : PathNoBoundOperator<T, FormulaType>(pathFormula, minimumOperator) {
// Intentionally left empty
}
/*!
* Destructor
*/
virtual ~RewardNoBoundOperator() {
// Intentionally left empty
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result = "R";
result += PathNoBoundOperator<T, FormulaType>::toString();
return result;
}
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_REWARDNOBOUNDOPERATOR_H_ */

174
src/formula/abstract/StateBoundOperator.h

@ -1,174 +0,0 @@
/*
* BoundOperator.h
*
* Created on: 27.12.2012
* Author: Christian Dehnert
*/
#ifndef STORM_FORMULA_ABSTRACT_STATEBOUNDOPERATOR_H_
#define STORM_FORMULA_ABSTRACT_STATEBOUNDOPERATOR_H_
#include "src/formula/abstract/AbstractFormula.h"
#include "src/formula/abstract/AbstractFormula.h"
#include "src/formula/AbstractFormulaChecker.h"
#include "src/formula/ComparisonType.h"
#include "src/utility/constants.h"
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract formula tree with a P (probablistic) operator node over a probability interval
* as root.
*
* Has one formula as sub formula/tree.
*
* @par Semantics
* The formula holds iff the probability that the state formula holds is inside the bounds
* specified in this operator
*
* The subtree is seen as part of the object and deleted with it
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "conforms" of the subformulas are needed.
*
* @see AbstractFormula
* @see StateNoBoundOperator
*/
template<class T, class FormulaType>
class StateBoundOperator : public virtual AbstractFormula<T> {
// Throw a compiler error if FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::StateBoundOperator<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/*!
* Constructor
*
* @param comparisonOperator The relation for the bound.
* @param bound The bound for the probability
* @param stateFormula The child node
*/
StateBoundOperator(storm::property::ComparisonType comparisonOperator, T bound, FormulaType* stateFormula)
: comparisonOperator(comparisonOperator), bound(bound), stateFormula(stateFormula) {
// Intentionally left empty
}
/*!
* Destructor
*
* The subtree is deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*/
virtual ~StateBoundOperator() {
if (stateFormula != nullptr) {
delete stateFormula;
}
}
/*!
* @returns the child node (representation of a formula)
*/
const FormulaType& getStateFormula () const {
return *stateFormula;
}
/*!
* Sets the child node
*
* @param stateFormula the state formula that becomes the new child node
*/
void setStateFormula(FormulaType* stateFormula) {
this->stateFormula = stateFormula;
}
/*!
*
* @return True if the state formula is set, i.e. it does not point to nullptr; false otherwise
*/
bool stateFormulaIsSet() const {
return stateFormula != nullptr;
}
/*!
* @returns the comparison relation
*/
const ComparisonType getComparisonOperator() const {
return comparisonOperator;
}
void setComparisonOperator(ComparisonType comparisonOperator) {
this->comparisonOperator = comparisonOperator;
}
/*!
* @returns the bound for the measure
*/
const T& getBound() const {
return bound;
}
/*!
* Sets the interval in which the probability that the path formula holds may lie in.
*
* @param bound The bound for the measure
*/
void setBound(T bound) {
this->bound = bound;
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result = " ";
switch (comparisonOperator) {
case LESS: result += "< "; break;
case LESS_EQUAL: result += "<= "; break;
case GREATER: result += "> "; break;
case GREATER_EQUAL: result += ">= "; break;
}
result += std::to_string(bound);
result += " [";
result += stateFormula->toString();
result += "]";
return result;
}
bool meetsBound(T value) const {
switch (comparisonOperator) {
case LESS: return value < bound; break;
case LESS_EQUAL: return value <= bound; break;
case GREATER: return value > bound; break;
case GREATER_EQUAL: return value >= bound; break;
default: return false;
}
}
/*!
* @brief Checks if the subtree conforms to some logic.
*
* @param checker Formula checker object.
* @return true iff the subtree conforms to some logic.
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const override {
return checker.validate(this->stateFormula);
}
private:
ComparisonType comparisonOperator;
T bound;
FormulaType* stateFormula;
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_STATEBOUNDOPERATOR_H_ */

126
src/formula/abstract/StateNoBoundOperator.h

@ -1,126 +0,0 @@
/*
* StateNoBoundOperator.h
*
* Created on: 09.04.2013
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_ABSTRACT_STATENOBOUNDOPERATOR_H_
#define STORM_FORMULA_ABSTRACT_STATENOBOUNDOPERATOR_H_
#include "AbstractFormula.h"
#include "src/formula/AbstractFormulaChecker.h"
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract formula tree with an operator without declaration of bounds.
* as root.
*
* Checking a formula with this operator as root returns the probabilities that the path formula holds
* (for each state)
*
* Has one formula as sub formula/tree.
*
* @note
* This class is a hybrid of a state and path formula, and may only appear as the outermost operator.
* Hence, it is seen as neither a state nor a path formula, but is directly derived from AbstractFormula.
*
* @note
* This class does not contain a check() method like the other formula classes.
* The check method should only be called by the model checker to infer the correct check function for sub
* formulas. As this operator can only appear at the root, the method is not useful here.
* Use the checkProbabilisticNoBoundOperator method from the DtmcPrctlModelChecker class instead.
*
* The subtree is seen as part of the object and deleted with it
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "conforms" of the subformulas are needed.
*
* @see AbstractFormula
* @see StateBoundOperator
*/
template <class T, class FormulaType>
class StateNoBoundOperator: public virtual AbstractFormula<T>, public OptimizingOperator {
// Throw a compiler error if FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::StateNoBoundOperator<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/*!
* Empty constructor
*/
StateNoBoundOperator() {
stateFormula = nullptr;
}
/*!
* Constructor
*/
StateNoBoundOperator(FormulaType* stateFormula) {
this->stateFormula = stateFormula;
}
/*!
* Destructor
*
* Deletes the subtree
*/
virtual ~StateNoBoundOperator() {
if (stateFormula != nullptr) {
delete stateFormula;
}
}
const FormulaType& getStateFormula() const {
return *(this->stateFormula);
}
void setStateFormula(FormulaType* stateFormula) {
this->stateFormula = stateFormula;
}
/*!
*
* @return True if the state formula is set, i.e. it does not point to nullptr; false otherwise
*/
bool stateFormulaIsSet() const {
return stateFormula != nullptr;
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result;
result += " = ? [";
result += this->getStateFormula().toString();
result += "]";
return result;
}
/*!
* @brief Checks if the subtree conforms to some logic.
*
* @param checker Formula checker object.
* @return true iff the subtree conforms to some logic.
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const override {
return checker.validate(this->stateFormula);
}
private:
FormulaType* stateFormula;
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_STATENOBOUNDOPERATOR_H_ */

77
src/formula/abstract/SteadyStateBoundOperator.h

@ -1,77 +0,0 @@
/*
* SteadyState.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_ABSTRACT_STEADYSTATEOPERATOR_H_
#define STORM_FORMULA_ABSTRACT_STEADYSTATEOPERATOR_H_
#include "StateBoundOperator.h"
#include "src/formula/AbstractFormulaChecker.h"
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an Abstract (path) formula tree with a SteadyStateOperator node as root.
*
* Has two formulas as sub formulas/trees.
*
* @par Semantics
* The formula holds iff \e child holds SteadyStateOperator step, \e child holds
*
* The subtree is seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @see AbstractFormula
*/
template <class T, class FormulaType>
class SteadyStateBoundOperator : public StateBoundOperator<T, FormulaType> {
// Throw a compiler error if FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::SteadyStateBoundOperator<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/*!
* Empty constructor
*/
SteadyStateBoundOperator() : StateBoundOperator<T, FormulaType>
(LESS_EQUAL, storm::utility::constantZero<T>(), nullptr) {
// Intentionally left empty
}
/*!
* Constructor
*
* @param stateFormula The child node
*/
SteadyStateBoundOperator(
storm::property::ComparisonType comparisonRelation, T bound, FormulaType* stateFormula) :
StateBoundOperator<T, FormulaType>(comparisonRelation, bound, stateFormula) {
}
/*!
* Destructor
*/
virtual ~SteadyStateBoundOperator() {
// Intentionally left empty
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
return "S" + StateBoundOperator<T, FormulaType>::toString();
}
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_STEADYSTATEOPERATOR_H_ */

76
src/formula/abstract/SteadyStateNoBoundOperator.h

@ -1,76 +0,0 @@
/*
* SteadyStateNoBoundOperator.h
*
* Created on: 09.04.2013
* Author: thomas
*/
#ifndef STORM_FORMULA_ABSTRACT_STEADYSTATENOBOUNDOPERATOR_H_
#define STORM_FORMULA_ABSTRACT_STEADYSTATENOBOUNDOPERATOR_H_
#include "StateNoBoundOperator.h"
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract formula tree with a steady state operator as root, without explicit declaration of bounds.
*
* Checking a formula with this operator as root returns the exact bound parameter for the corresponding subformula.
* (for each state)
*
* Has one formula as sub formula/tree.
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "conforms" of the subformulas are needed.
*/
template <class T, class FormulaType>
class SteadyStateNoBoundOperator: public StateNoBoundOperator<T, FormulaType> {
// Throw a compiler error if FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::SteadyStateNoBoundOperator<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/*!
* Empty constructor
*/
SteadyStateNoBoundOperator() : StateNoBoundOperator<T, FormulaType>() {
// Intentionally left empty
}
/*!
* Constructor
*
* @param stateFormula The state formula that forms the subtree
*/
SteadyStateNoBoundOperator(FormulaType* stateFormula)
: StateNoBoundOperator<T, FormulaType>(stateFormula) {
// Intentionally left empty
}
/*!
* Destructor
*/
virtual ~SteadyStateNoBoundOperator() {
// Intentionally left empty
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
return "S" + StateNoBoundOperator<T, FormulaType>::toString();
}
};
} /* namespace abstract */
} /* namespace property */
} /* namespace storm */
#endif /* STORM_FORMULA_ABSTRACT_STEADYSTATENOBOUNDOPERATOR_H_ */

62
src/formula/abstract/SteadyStateReward.h

@ -1,62 +0,0 @@
/*
* SteadyStateReward.h
*
* Created on: 08.04.2013
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_ABSTRACT_STEADYSTATEREWARD_H_
#define STORM_FORMULA_ABSTRACT_STEADYSTATEREWARD_H_
#include "AbstractFormula.h"
#include "src/formula/AbstractFormulaChecker.h"
#include <string>
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract (path) formula tree with a Steady State Reward node as root.
*
* @see AbstractFormula
*/
template <class T>
class SteadyStateReward: public virtual AbstractFormula<T> {
public:
/*!
* Empty constructor
*/
SteadyStateReward() {
// Intentionally left empty
}
virtual ~SteadyStateReward() {
// Intentionally left empty
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
return "S";
}
/*!
* @brief Checks if all subtrees conform to some logic.
*
* As SteadyStateReward objects have no subformulas, we return true here.
*
* @param checker Formula checker object.
* @return true
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const override {
return true;
}
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_STEADYSTATEREWARD_H_ */

107
src/formula/abstract/TimeBoundedEventually.h

@ -1,107 +0,0 @@
/*
* TimeBoundedEventually.h
*
* Created on: 10.04.2013
* Author: thomas
*/
#ifndef STORM_FORMULA_ABSTRACT_TIMEBOUNDEDEVENTUALLY_H_
#define STORM_FORMULA_ABSTRACT_TIMEBOUNDEDEVENTUALLY_H_
#include "TimeBoundedOperator.h"
namespace storm {
namespace property {
namespace abstract {
/*!
* Class for a formula tree with a time bounded eventually operator as root.
*
* Has two subformulas.
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "conforms" of the subformulas are needed.
*/
template<class T, class FormulaType>
class TimeBoundedEventually: public storm::property::abstract::TimeBoundedOperator<T> {
// Throw a compiler error if FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::TimeBoundedEventually<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/**
* Simple constructor: Only sets the bounds
*
* @param lowerBound
* @param upperBound
*/
TimeBoundedEventually(T lowerBound, T upperBound) : TimeBoundedOperator<T>(lowerBound, upperBound) {
child = nullptr;
}
TimeBoundedEventually(T lowerBound, T upperBound, FormulaType* child) :
TimeBoundedOperator<T>(lowerBound, upperBound) {
this->child = child;
}
virtual ~TimeBoundedEventually() {
if (child != nullptr) {
delete child;
}
}
/*!
* @returns the child node
*/
const FormulaType& getChild() const {
return *child;
}
/*!
* Sets the subtree
* @param child the new child node
*/
void setChild(FormulaType* child) {
this->child = child;
}
/*!
*
* @return True if the child is set, i.e. it does not point to nullptr; false otherwise
*/
bool childIsSet() const {
return child != nullptr;
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result = "F";
result += TimeBoundedOperator<T>::toString();
result += " ";
result += child->toString();
return result;
}
/*!
* @brief Checks if the subtree conforms to some logic.
*
* @param checker Formula checker object.
* @return true iff the subtree conforms to some logic.
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const override {
return checker.validate(this->child);
}
private:
FormulaType* child;
};
} /* namespace abstract */
} /* namespace property */
} /* namespace storm */
#endif /* STORM_FORMULA_ABSTRACT_TIMEBOUNDEDEVENTUALLY_H_ */

112
src/formula/abstract/TimeBoundedOperator.h

@ -1,112 +0,0 @@
/*
* TimeBoundedOperator.h
*
* Created on: 10.04.2013
* Author: thomas
*/
#ifndef STORM_FORMULA_ABSTRACT_TIMEBOUNDEDOPERATOR_H_
#define STORM_FORMULA_ABSTRACT_TIMEBOUNDEDOPERATOR_H_
#include <limits>
#include "src/formula/abstract/AbstractFormula.h"
#include "exceptions/InvalidArgumentException.h"
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract formula tree with a operator node as root that uses a time interval
* (with upper and lower bound)
*
* This class does not provide support for sub formulas; this has to be done in concrete subclasses of this abstract class.
*
*
* @see AbstractFormula
* @see AbstractFormula
* @see AbstractFormula
*/
template<class T>
class TimeBoundedOperator: public virtual AbstractFormula<T> {
public:
/**
* Constructor
*
* @param lowerBound The lower bound
* @param upperBound The upper bound
* @throw InvalidArgumentException if the lower bound is larger than the upper bound.
*/
TimeBoundedOperator(T lowerBound, T upperBound) {
setInterval(lowerBound, upperBound);
}
/**
* Destructor
*/
virtual ~TimeBoundedOperator() {
// Intentionally left empty
}
/**
* Getter for lowerBound attribute
*
* @return lower bound of the operator.
*/
T getLowerBound() const {
return lowerBound;
}
/**
* Getter for upperBound attribute
* @return upper bound of the operator.
*/
T getUpperBound() const {
return upperBound;
}
/**
* Set the time interval for the time bounded operator
*
* @param lowerBound
* @param upperBound
* @throw InvalidArgumentException if the lower bound is larger than the upper bound.
*/
void setInterval(T lowerBound, T upperBound) {
if (lowerBound > upperBound) {
throw new storm::exceptions::InvalidArgumentException("Lower bound is larger than upper bound");
}
this->lowerBound = lowerBound;
this->upperBound = upperBound;
}
/*!
* @returns a string representation of the Interval of the formula
* May be used in subclasses to simplify string output.
*/
virtual std::string toString() const override {
std::string result = "";
if (upperBound == std::numeric_limits<double>::infinity()) {
result = ">=" + std::to_string(lowerBound);
} else {
result = "[";
result += std::to_string(lowerBound);
result += ",";
result += std::to_string(upperBound);
result += "]";
}
return result;
}
private:
T lowerBound, upperBound;
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_TIMEBOUNDEDOPERATOR_H_ */

149
src/formula/abstract/TimeBoundedUntil.h

@ -1,149 +0,0 @@
/*
* TimeBoundedUntil.h
*
* Created on: 10.04.2013
* Author: thomas
*/
#ifndef STORM_FORMULA_ABSTRACT_TIMEBOUNDEDUNTIL_H_
#define STORM_FORMULA_ABSTRACT_TIMEBOUNDEDUNTIL_H_
#include "TimeBoundedOperator.h"
namespace storm {
namespace property {
namespace abstract {
/**
* @brief
* Class for an abstract formula tree with an time bounded until operator as root.
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "conforms" of the subformulas are needed.
*/
template <class T, class FormulaType>
class TimeBoundedUntil: public TimeBoundedOperator<T> {
// Throw a compiler error if FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::TimeBoundedUntil<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/**
* Constructor providing bounds only;
* Sub formulas are set to null.
*
* @param lowerBound
* @param upperBound
*/
TimeBoundedUntil(T lowerBound, T upperBound) :
TimeBoundedOperator<T>(lowerBound, upperBound) {
this->left = nullptr;
this->right = nullptr;
}
/**
* Full constructor
* @param lowerBound
* @param upperBound
* @param left
* @param right
*/
TimeBoundedUntil(T lowerBound, T upperBound, FormulaType* left, FormulaType* right) :
TimeBoundedOperator<T>(lowerBound, upperBound) {
this->left = left;
this->right = right;
}
virtual ~TimeBoundedUntil() {
if (left != nullptr) {
delete left;
}
if (right != nullptr) {
delete right;
}
}
/*!
* Sets the left child node.
*
* @param newLeft the new left child.
*/
void setLeft(FormulaType* newLeft) {
left = newLeft;
}
/*!
* Sets the right child node.
*
* @param newRight the new right child.
*/
void setRight(FormulaType* newRight) {
right = newRight;
}
/*!
* @returns a pointer to the left child node
*/
const FormulaType& getLeft() const {
return *left;
}
/*!
* @returns a pointer to the right child node
*/
const FormulaType& getRight() const {
return *right;
}
/*!
*
* @return True if the left child is set, i.e. it does not point to nullptr; false otherwise
*/
bool leftIsSet() const {
return left != nullptr;
}
/*!
*
* @return True if the right child is set, i.e. it does not point to nullptr; false otherwise
*/
bool rightIsSet() const {
return right != nullptr;
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result = left->toString();
result += " U";
result += TimeBoundedOperator<T>::toString();
result += " ";
result += right->toString();
return result;
}
/*!
* @brief Checks if the subtree conforms to some logic.
*
* @param checker Formula checker object.
* @return true iff the subtree conforms to some logic.
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const override {
return checker.validate(this->left) && checker.validate(this->right);
}
private:
FormulaType* left;
FormulaType* right;
};
} /* namespace abstract */
} /* namespace property */
} /* namespace storm */
#endif /* STORM_FORMULA_ABSTRACT_TIMEBOUNDEDUNTIL_H_ */

159
src/formula/abstract/Until.h

@ -1,159 +0,0 @@
/*
* Until.h
*
* Created on: 19.10.2012
* Author: Thomas Heinemann
*/
#ifndef STORM_FORMULA_ABSTRACT_UNTIL_H_
#define STORM_FORMULA_ABSTRACT_UNTIL_H_
#include "src/formula/abstract/AbstractFormula.h"
#include "src/formula/abstract/AbstractFormula.h"
#include "src/formula/AbstractFormulaChecker.h"
namespace storm {
namespace property {
namespace abstract {
/*!
* @brief
* Class for an abstract (path) formula tree with an Until node as root.
*
* Has two formulas as sub formulas/trees.
*
* @par Semantics
* The formula holds iff eventually, formula \e right (the right subtree) holds, and before,
* \e left holds always.
*
* The subtrees are seen as part of the object and deleted with the object
* (this behavior can be prevented by setting them to NULL before deletion)
*
* @tparam FormulaType The type of the subformula.
* The instantiation of FormulaType should be a subclass of AbstractFormula, as the functions
* "toString" and "conforms" of the subformulas are needed.
*
* @see AbstractFormula
*/
template <class T, class FormulaType>
class Until : public virtual AbstractFormula<T> {
// Throw a compiler error if FormulaType is not a subclass of AbstractFormula.
static_assert(std::is_base_of<AbstractFormula<T>, FormulaType>::value,
"Instantiaton of FormulaType for storm::property::abstract::Until<T,FormulaType> has to be a subtype of storm::property::abstract::AbstractFormula<T>");
public:
/*!
* Empty constructor
*/
Until() {
this->left = NULL;
this->right = NULL;
}
/*!
* Constructor
*
* @param left The left formula subtree
* @param right The left formula subtree
*/
Until(FormulaType* left, FormulaType* right) {
this->left = left;
this->right = right;
}
/*!
* Destructor.
*
* Also deletes the subtrees.
* (this behaviour can be prevented by setting the subtrees to NULL before deletion)
*/
virtual ~Until() {
if (left != NULL) {
delete left;
}
if (right != NULL) {
delete right;
}
}
/*!
* Sets the left child node.
*
* @param newLeft the new left child.
*/
void setLeft(FormulaType* newLeft) {
left = newLeft;
}
/*!
* Sets the right child node.
*
* @param newRight the new right child.
*/
void setRight(FormulaType* newRight) {
right = newRight;
}
/*!
* @returns a pointer to the left child node
*/
const FormulaType& getLeft() const {
return *left;
}
/*!
* @returns a pointer to the right child node
*/
const FormulaType& getRight() const {
return *right;
}
/*!
*
* @return True if the left child is set, i.e. it does not point to nullptr; false otherwise
*/
bool leftIsSet() const {
return left != nullptr;
}
/*!
*
* @return True if the right child is set, i.e. it does not point to nullptr; false otherwise
*/
bool rightIsSet() const {
return right != nullptr;
}
/*!
* @returns a string representation of the formula
*/
virtual std::string toString() const override {
std::string result = left->toString();
result += " U ";
result += right->toString();
return result;
}
/*!
* @brief Checks if all subtrees conform to some logic.
*
* @param checker Formula checker object.
* @return true iff all subtrees conform to some logic.
*/
virtual bool validate(const AbstractFormulaChecker<T>& checker) const override {
return checker.validate(this->left) && checker.validate(this->right);
}
private:
FormulaType* left;
FormulaType* right;
};
} //namespace abstract
} //namespace property
} //namespace storm
#endif /* STORM_FORMULA_ABSTRACT_UNTIL_H_ */

155
src/modelchecker/csl/AbstractModelChecker.h

@ -8,8 +8,9 @@
#ifndef STORM_MODELCHECKER_CSL_ABSTRACTMODELCHECKER_H_
#define STORM_MODELCHECKER_CSL_ABSTRACTMODELCHECKER_H_
#include <stack>
#include "src/exceptions/InvalidPropertyException.h"
#include "src/formula/Csl.h"
#include "src/properties/Csl.h"
#include "src/storage/BitVector.h"
#include "src/models/AbstractModel.h"
@ -36,31 +37,30 @@ template<class Type>
class AbstractModelChecker :
// A list of interfaces the model checker supports. Typically, for each of the interfaces, a check method needs to
// be implemented that performs the corresponding check.
public virtual storm::property::csl::IApModelChecker<Type>,
public virtual storm::property::csl::IAndModelChecker<Type>,
public virtual storm::property::csl::IOrModelChecker<Type>,
public virtual storm::property::csl::INotModelChecker<Type>,
public virtual storm::property::csl::IUntilModelChecker<Type>,
public virtual storm::property::csl::IEventuallyModelChecker<Type>,
public virtual storm::property::csl::IGloballyModelChecker<Type>,
public virtual storm::property::csl::INextModelChecker<Type>,
public virtual storm::property::csl::ITimeBoundedUntilModelChecker<Type>,
public virtual storm::property::csl::ITimeBoundedEventuallyModelChecker<Type>,
public virtual storm::property::csl::INoBoundOperatorModelChecker<Type>,
public virtual storm::property::csl::IProbabilisticBoundOperatorModelChecker<Type> {
public virtual storm::properties::csl::IApModelChecker<Type>,
public virtual storm::properties::csl::IAndModelChecker<Type>,
public virtual storm::properties::csl::IOrModelChecker<Type>,
public virtual storm::properties::csl::INotModelChecker<Type>,
public virtual storm::properties::csl::IUntilModelChecker<Type>,
public virtual storm::properties::csl::IEventuallyModelChecker<Type>,
public virtual storm::properties::csl::IGloballyModelChecker<Type>,
public virtual storm::properties::csl::INextModelChecker<Type>,
public virtual storm::properties::csl::ITimeBoundedUntilModelChecker<Type>,
public virtual storm::properties::csl::ITimeBoundedEventuallyModelChecker<Type>,
public virtual storm::properties::csl::IProbabilisticBoundOperatorModelChecker<Type> {
public:
/*!
* Constructs an AbstractModelChecker with the given model.
*/
explicit AbstractModelChecker(storm::models::AbstractModel<Type> const& model) : model(model) {
explicit AbstractModelChecker(storm::models::AbstractModel<Type> const& model) : minimumOperatorStack(), model(model) {
// Intentionally left empty.
}
/*!
* Copy constructs an AbstractModelChecker from the given model checker. In particular, this means that the newly
* constructed model checker will have the model of the given model checker as its associated model.
*/
explicit AbstractModelChecker(AbstractModelChecker<Type> const& modelchecker) : model(modelchecker.model) {
explicit AbstractModelChecker(AbstractModelChecker<Type> const& modelchecker) : minimumOperatorStack(), model(modelchecker.model) {
// Intentionally left empty.
}
@ -106,78 +106,13 @@ public:
}
}
/*!
* Checks the given abstract prctl formula on the model and prints the result (depending on the actual type of the formula)
* for all initial states, i.e. states that carry the atomic proposition "init".
*
* @param formula The formula to be checked.
*/
void check(storm::property::csl::AbstractCslFormula<Type> const& formula) const {
if (dynamic_cast<storm::property::csl::AbstractStateFormula<Type> const*>(&formula) != nullptr) {
this->check(static_cast<storm::property::csl::AbstractStateFormula<Type> const&>(formula));
} else if (dynamic_cast<storm::property::csl::AbstractNoBoundOperator<Type> const*>(&formula) != nullptr) {
this->check(static_cast<storm::property::csl::AbstractNoBoundOperator<Type> const&>(formula));
}
}
/*!
* Checks the given state formula on the model and prints the result (true/false) for all initial states, i.e.
* states that carry the atomic proposition "init".
*
* @param stateFormula The formula to be checked.
*/
void check(storm::property::csl::AbstractStateFormula<Type> const& stateFormula) const {
std::cout << std::endl;
LOG4CPLUS_INFO(logger, "Model checking formula\t" << stateFormula.toString());
std::cout << "Model checking formula:\t" << stateFormula.toString() << std::endl;
storm::storage::BitVector result;
try {
result = stateFormula.check(*this);
LOG4CPLUS_INFO(logger, "Result for initial states:");
std::cout << "Result for initial states:" << std::endl;
for (auto initialState : model.getInitialStates()) {
LOG4CPLUS_INFO(logger, "\t" << initialState << ": " << (result.get(initialState) ? "satisfied" : "not satisfied"));
std::cout << "\t" << initialState << ": " << result.get(initialState) << std::endl;
}
} catch (std::exception& e) {
std::cout << "Error during computation: " << e.what() << "Skipping property." << std::endl;
LOG4CPLUS_ERROR(logger, "Error during computation: " << e.what() << "Skipping property.");
}
std::cout << std::endl << "-------------------------------------------" << std::endl;
}
/*!
* Checks the given formula (with no bound) on the model and prints the result (probability/rewards) for all
* initial states, i.e. states that carry the atomic proposition "init".
*
* @param noBoundFormula The formula to be checked.
*/
void check(storm::property::csl::AbstractNoBoundOperator<Type> const& noBoundFormula) const {
std::cout << std::endl;
LOG4CPLUS_INFO(logger, "Model checking formula\t" << noBoundFormula.toString());
std::cout << "Model checking formula:\t" << noBoundFormula.toString() << std::endl;
std::vector<Type> result;
try {
result = this->checkNoBoundOperator(noBoundFormula);
LOG4CPLUS_INFO(logger, "Result for initial states:");
std::cout << "Result for initial states:" << std::endl;
for (auto initialState : model.getInitialStates()) {
LOG4CPLUS_INFO(logger, "\t" << initialState << ": " << (*result)[initialState]);
std::cout << "\t" << initialState << ": " << (*result)[initialState] << std::endl;
}
} catch (std::exception& e) {
std::cout << "Error during computation: " << e.what() << " Skipping property." << std::endl;
}
std::cout << std::endl << "-------------------------------------------" << std::endl;
}
/*!
* Checks the given formula consisting of a single atomic proposition.
*
* @param formula The formula to be checked.
* @returns The set of states satisfying the formula represented by a bit vector.
*/
storm::storage::BitVector checkAp(storm::property::csl::Ap<Type> const& formula) const {
storm::storage::BitVector checkAp(storm::properties::csl::Ap<Type> const& formula) const {
if (formula.getAp() == "true") {
return storm::storage::BitVector(model.getNumberOfStates(), true);
} else if (formula.getAp() == "false") {
@ -198,9 +133,9 @@ public:
* @param formula The formula to be checked.
* @returns The set of states satisfying the formula represented by a bit vector.
*/
storm::storage::BitVector checkAnd(storm::property::csl::And<Type> const& formula) const {
storm::storage::BitVector result = formula.getLeft().check(*this);
storm::storage::BitVector right = formula.getRight().check(*this);
storm::storage::BitVector checkAnd(storm::properties::csl::And<Type> const& formula) const {
storm::storage::BitVector result = formula.getLeft()->check(*this);
storm::storage::BitVector right = formula.getRight()->check(*this);
result &= right;
return result;
}
@ -211,9 +146,9 @@ public:
* @param formula The formula to check.
* @returns The set of states satisfying the formula represented by a bit vector.
*/
storm::storage::BitVector checkOr(storm::property::csl::Or<Type> const& formula) const {
storm::storage::BitVector result = formula.getLeft().check(*this);
storm::storage::BitVector right = formula.getRight().check(*this);
storm::storage::BitVector checkOr(storm::properties::csl::Or<Type> const& formula) const {
storm::storage::BitVector result = formula.getLeft()->check(*this);
storm::storage::BitVector right = formula.getRight()->check(*this);
result |= right;
return result;
}
@ -224,8 +159,8 @@ public:
* @param formula The formula to check.
* @returns The set of states satisfying the formula represented by a bit vector.
*/
storm::storage::BitVector checkNot(const storm::property::csl::Not<Type>& formula) const {
storm::storage::BitVector result = formula.getChild().check(*this);
storm::storage::BitVector checkNot(const storm::properties::csl::Not<Type>& formula) const {
storm::storage::BitVector result = formula.getChild()->check(*this);
result.complement();
return result;
}
@ -237,9 +172,9 @@ public:
* @param formula The formula to check.
* @returns The set of states satisfying the formula represented by a bit vector.
*/
storm::storage::BitVector checkProbabilisticBoundOperator(storm::property::csl::ProbabilisticBoundOperator<Type> const& formula) const {
virtual storm::storage::BitVector checkProbabilisticBoundOperator(storm::properties::csl::ProbabilisticBoundOperator<Type> const& formula) const {
// First, we need to compute the probability for satisfying the path formula for each state.
std::vector<Type> quantitativeResult = formula.getPathFormula().check(*this, false);
std::vector<Type> quantitativeResult = formula.getChild()->check(*this, false);
// Create resulting bit vector that will hold the yes/no-answer for every state.
storm::storage::BitVector result(quantitativeResult.size());
@ -255,6 +190,42 @@ public:
return result;
}
/*!
* Checks the given formula and determines whether minimum or maximum probabilities or rewards are to be computed for the formula.
*
* @param formula The formula to check.
* @param minimumOperator True iff minimum probabilities/rewards are to be computed.
* @returns The probabilities to satisfy the formula or the rewards accumulated by it, represented by a vector.
*/
virtual std::vector<Type> checkMinMaxOperator(storm::properties::csl::AbstractPathFormula<Type> const & formula, bool minimumOperator) const {
minimumOperatorStack.push(minimumOperator);
std::vector<Type> result = formula.check(*this, false);
minimumOperatorStack.pop();
return result;
}
/*!
* Checks the given formula and determines whether minimum or maximum probabilities or rewards are to be computed for the formula.
*
* @param formula The formula to check.
* @param minimumOperator True iff minimum probabilities/rewards are to be computed.
* @returns The set of states satisfying the formula represented by a bit vector.
*/
virtual storm::storage::BitVector checkMinMaxOperator(storm::properties::csl::AbstractStateFormula<Type> const & formula, bool minimumOperator) const {
minimumOperatorStack.push(minimumOperator);
storm::storage::BitVector result = formula.check(*this);
minimumOperatorStack.pop();
return result;
}
protected:
/*!
* A stack used for storing whether we are currently computing min or max probabilities or rewards, respectively.
* The topmost element is true if and only if we are currently computing minimum probabilities or rewards.
*/
mutable std::stack<bool> minimumOperatorStack;
private:
/*!
@ -270,4 +241,4 @@ private:
} // namespace modelchecker
} // namespace storm
#endif /* STORM_MODELCHECKER_CSL_DTMCPRCTLMODELCHECKER_H_ */
#endif /* STORM_MODELCHECKER_CSL_ABSTRACTMODELCHECKER_H_ */

105
src/modelchecker/csl/SparseMarkovAutomatonCslModelChecker.h

@ -1,7 +1,6 @@
#ifndef STORM_MODELCHECKER_CSL_SPARSEMARKOVAUTOMATONCSLMODELCHECKER_H_
#define STORM_MODELCHECKER_CSL_SPARSEMARKOVAUTOMATONCSLMODELCHECKER_H_
#include <stack>
#include <utility>
#include "src/modelchecker/csl/AbstractModelChecker.h"
@ -22,7 +21,7 @@ namespace storm {
template<typename ValueType>
class SparseMarkovAutomatonCslModelChecker : public AbstractModelChecker<ValueType> {
public:
explicit SparseMarkovAutomatonCslModelChecker(storm::models::MarkovAutomaton<ValueType> const& model, std::shared_ptr<storm::solver::NondeterministicLinearEquationSolver<ValueType>> nondeterministicLinearEquationSolver) : AbstractModelChecker<ValueType>(model), minimumOperatorStack(), nondeterministicLinearEquationSolver(nondeterministicLinearEquationSolver) {
explicit SparseMarkovAutomatonCslModelChecker(storm::models::MarkovAutomaton<ValueType> const& model, std::shared_ptr<storm::solver::NondeterministicLinearEquationSolver<ValueType>> nondeterministicLinearEquationSolver) : AbstractModelChecker<ValueType>(model), nondeterministicLinearEquationSolver(nondeterministicLinearEquationSolver) {
// Intentionally left empty.
}
@ -30,7 +29,14 @@ namespace storm {
This Second constructor is NEEDED and a workaround for a common Bug in C++ with nested templates
See: http://stackoverflow.com/questions/14401308/visual-c-cannot-deduce-given-template-arguments-for-function-used-as-defaul
*/
explicit SparseMarkovAutomatonCslModelChecker(storm::models::MarkovAutomaton<ValueType> const& model) : AbstractModelChecker<ValueType>(model), minimumOperatorStack(), nondeterministicLinearEquationSolver(storm::utility::solver::getNondeterministicLinearEquationSolver<ValueType>()) {
explicit SparseMarkovAutomatonCslModelChecker(storm::models::MarkovAutomaton<ValueType> const& model) : AbstractModelChecker<ValueType>(model), nondeterministicLinearEquationSolver(storm::utility::solver::getNondeterministicLinearEquationSolver<ValueType>()) {
// Intentionally left empty.
}
/*!
* Virtual destructor. Needs to be virtual, because this class has virtual methods.
*/
virtual ~SparseMarkovAutomatonCslModelChecker() {
// Intentionally left empty.
}
@ -42,50 +48,89 @@ namespace storm {
return AbstractModelChecker<ValueType>::template getModel<storm::models::MarkovAutomaton<ValueType>>();
}
std::vector<ValueType> checkUntil(storm::property::csl::Until<ValueType> const& formula, bool qualitative) const {
storm::storage::BitVector leftStates = formula.getLeft().check(*this);
storm::storage::BitVector rightStates = formula.getRight().check(*this);
return computeUnboundedUntilProbabilities(minimumOperatorStack.top(), leftStates, rightStates, qualitative).first;
/*!
* Checks the given formula that is a P operator over a path formula featuring a value bound.
*
* @param formula The formula to check.
* @returns The set of states satisfying the formula represented by a bit vector.
*/
virtual storm::storage::BitVector checkProbabilisticBoundOperator(storm::properties::csl::ProbabilisticBoundOperator<ValueType> const& formula) const override{
// For P< and P<= the MA satisfies the formula iff the probability maximizing scheduler is used.
// For P> and P>= " iff the probability minimizing " .
if(formula.getComparisonOperator() == storm::properties::LESS || formula.getComparisonOperator() == storm::properties::LESS_EQUAL) {
this->minimumOperatorStack.push(false);
}
else {
this->minimumOperatorStack.push(true);
}
// First, we need to compute the probability for satisfying the path formula for each state.
std::vector<ValueType> quantitativeResult = formula.getChild()->check(*this, false);
//Remove the minimizing operator entry from the stack.
this->minimumOperatorStack.pop();
// Create resulting bit vector that will hold the yes/no-answer for every state.
storm::storage::BitVector result(quantitativeResult.size());
// Now, we can compute which states meet the bound specified in this operator and set the
// corresponding bits to true in the resulting vector.
for (uint_fast64_t i = 0; i < quantitativeResult.size(); ++i) {
if (formula.meetsBound(quantitativeResult[i])) {
result.set(i, true);
}
}
return result;
}
std::vector<ValueType> checkUntil(storm::properties::csl::Until<ValueType> const& formula, bool qualitative) const {
// Test wheter it is specified if the minimum or the maximum probabilities are to be computed.
if(this->minimumOperatorStack.empty()) {
LOG4CPLUS_ERROR(logger, "Formula does not specify either min or max optimality, which is not meaningful over nondeterministic models.");
throw storm::exceptions::InvalidArgumentException() << "Formula does not specify either min or max optimality, which is not meaningful over nondeterministic models.";
}
storm::storage::BitVector leftStates = formula.getLeft()->check(*this);
storm::storage::BitVector rightStates = formula.getRight()->check(*this);
return computeUnboundedUntilProbabilities(this->minimumOperatorStack.top(), leftStates, rightStates, qualitative).first;
}
std::pair<std::vector<ValueType>, storm::storage::TotalScheduler> computeUnboundedUntilProbabilities(bool min, storm::storage::BitVector const& leftStates, storm::storage::BitVector const& rightStates, bool qualitative) const {
return storm::modelchecker::prctl::SparseMdpPrctlModelChecker<ValueType>::computeUnboundedUntilProbabilities(min, this->getModel().getTransitionMatrix(), this->getModel().getBackwardTransitions(), this->getModel().getInitialStates(), leftStates, rightStates, nondeterministicLinearEquationSolver, qualitative);
}
std::vector<ValueType> checkTimeBoundedUntil(storm::property::csl::TimeBoundedUntil<ValueType> const& formula, bool qualitative) const {
std::vector<ValueType> checkTimeBoundedUntil(storm::properties::csl::TimeBoundedUntil<ValueType> const& formula, bool qualitative) const {
throw storm::exceptions::NotImplementedException() << "Model checking Until formulas on Markov automata is not yet implemented.";
}
std::vector<ValueType> checkTimeBoundedEventually(storm::property::csl::TimeBoundedEventually<ValueType> const& formula, bool qualitative) const {
storm::storage::BitVector goalStates = formula.getChild().check(*this);
std::vector<ValueType> checkTimeBoundedEventually(storm::properties::csl::TimeBoundedEventually<ValueType> const& formula, bool qualitative) const {
// Test wheter it is specified if the minimum or the maximum probabilities are to be computed.
if(this->minimumOperatorStack.empty()) {
LOG4CPLUS_ERROR(logger, "Formula does not specify either min or max optimality, which is not meaningful over nondeterministic models.");
throw storm::exceptions::InvalidArgumentException() << "Formula does not specify either min or max optimality, which is not meaningful over nondeterministic models.";
}
storm::storage::BitVector goalStates = formula.getChild()->check(*this);
return this->checkTimeBoundedEventually(this->minimumOperatorStack.top(), goalStates, formula.getLowerBound(), formula.getUpperBound());
}
std::vector<ValueType> checkGlobally(storm::property::csl::Globally<ValueType> const& formula, bool qualitative) const {
std::vector<ValueType> checkGlobally(storm::properties::csl::Globally<ValueType> const& formula, bool qualitative) const {
throw storm::exceptions::NotImplementedException() << "Model checking Globally formulas on Markov automata is not yet implemented.";
}
std::vector<ValueType> checkEventually(storm::property::csl::Eventually<ValueType> const& formula, bool qualitative) const {
storm::storage::BitVector subFormulaStates = formula.getChild().check(*this);
return computeUnboundedUntilProbabilities(minimumOperatorStack.top(), storm::storage::BitVector(this->getModel().getNumberOfStates(), true), subFormulaStates, qualitative).first;
std::vector<ValueType> checkEventually(storm::properties::csl::Eventually<ValueType> const& formula, bool qualitative) const {
// Test wheter it is specified if the minimum or the maximum probabilities are to be computed.
if(this->minimumOperatorStack.empty()) {
LOG4CPLUS_ERROR(logger, "Formula does not specify either min or max optimality, which is not meaningful over nondeterministic models.");
throw storm::exceptions::InvalidArgumentException() << "Formula does not specify either min or max optimality, which is not meaningful over nondeterministic models.";
}
storm::storage::BitVector subFormulaStates = formula.getChild()->check(*this);
return computeUnboundedUntilProbabilities(this->minimumOperatorStack.top(), storm::storage::BitVector(this->getModel().getNumberOfStates(), true), subFormulaStates, qualitative).first;
}
std::vector<ValueType> checkNext(storm::property::csl::Next<ValueType> const& formula, bool qualitative) const {
std::vector<ValueType> checkNext(storm::properties::csl::Next<ValueType> const& formula, bool qualitative) const {
throw storm::exceptions::NotImplementedException() << "Model checking Next formulas on Markov automata is not yet implemented.";
}
std::vector<ValueType> checkNoBoundOperator(storm::property::csl::AbstractNoBoundOperator<ValueType> const& formula) const {
// Check if the operator was an non-optimality operator and report an error in that case.
if (!formula.isOptimalityOperator()) {
LOG4CPLUS_ERROR(logger, "Formula does not specify neither min nor max optimality, which is not meaningful for nondeterministic models.");
throw storm::exceptions::InvalidArgumentException() << "Formula does not specify neither min nor max optimality, which is not meaningful for nondeterministic models.";
}
minimumOperatorStack.push(formula.isMinimumOperator());
std::vector<ValueType> result = formula.check(*this, false);
minimumOperatorStack.pop();
return result;
}
static void computeBoundedReachabilityProbabilities(bool min, storm::storage::SparseMatrix<ValueType> const& transitionMatrix, std::vector<ValueType> const& exitRates, storm::storage::BitVector const& markovianStates, storm::storage::BitVector const& goalStates, storm::storage::BitVector const& markovianNonGoalStates, storm::storage::BitVector const& probabilisticNonGoalStates, std::vector<ValueType>& markovianNonGoalValues, std::vector<ValueType>& probabilisticNonGoalValues, ValueType delta, uint_fast64_t numberOfSteps) {
// Start by computing four sparse matrices:
// * a matrix aMarkovian with all (discretized) transitions from Markovian non-goal states to all Markovian non-goal states.
@ -580,12 +625,6 @@ namespace storm {
return result;
}
/*!
* A stack used for storing whether we are currently computing min or max probabilities or rewards, respectively.
* The topmost element is true if and only if we are currently computing minimum probabilities or rewards.
*/
mutable std::stack<bool> minimumOperatorStack;
/*!
* A solver that is used for solving systems of linear equations that are the result of nondeterministic choices.
*/

56
src/modelchecker/ltl/AbstractModelChecker.h

@ -9,7 +9,7 @@
#define STORM_MODELCHECKER_LTL_ABSTRACTMODELCHECKER_H_
#include "src/exceptions/InvalidPropertyException.h"
#include "src/formula/Ltl.h"
#include "src/properties/Ltl.h"
#include "src/storage/BitVector.h"
#include "src/models/AbstractModel.h"
@ -36,16 +36,16 @@ template<class Type>
class AbstractModelChecker :
// A list of interfaces the model checker supports. Typically, for each of the interfaces, a check method needs to
// be implemented that performs the corresponding check.
public virtual storm::property::ltl::IApModelChecker<Type>,
public virtual storm::property::ltl::IAndModelChecker<Type>,
public virtual storm::property::ltl::IOrModelChecker<Type>,
public virtual storm::property::ltl::INotModelChecker<Type>,
public virtual storm::property::ltl::IUntilModelChecker<Type>,
public virtual storm::property::ltl::IEventuallyModelChecker<Type>,
public virtual storm::property::ltl::IGloballyModelChecker<Type>,
public virtual storm::property::ltl::INextModelChecker<Type>,
public virtual storm::property::ltl::IBoundedUntilModelChecker<Type>,
public virtual storm::property::ltl::IBoundedEventuallyModelChecker<Type> {
public virtual storm::properties::ltl::IApModelChecker<Type>,
public virtual storm::properties::ltl::IAndModelChecker<Type>,
public virtual storm::properties::ltl::IOrModelChecker<Type>,
public virtual storm::properties::ltl::INotModelChecker<Type>,
public virtual storm::properties::ltl::IUntilModelChecker<Type>,
public virtual storm::properties::ltl::IEventuallyModelChecker<Type>,
public virtual storm::properties::ltl::IGloballyModelChecker<Type>,
public virtual storm::properties::ltl::INextModelChecker<Type>,
public virtual storm::properties::ltl::IBoundedUntilModelChecker<Type>,
public virtual storm::properties::ltl::IBoundedEventuallyModelChecker<Type> {
public:
/*!
@ -104,39 +104,13 @@ public:
}
}
/*!
* Checks the given state formula on the model and prints the result (true/false) for all initial states, i.e.
* states that carry the atomic proposition "init".
*
* @param stateFormula The formula to be checked.
*/
void check(storm::property::ltl::AbstractLtlFormula<Type> const& ltlFormula) const {
std::cout << std::endl;
LOG4CPLUS_INFO(logger, "Model checking formula\t" << ltlFormula.toString());
std::cout << "Model checking formula:\t" << ltlFormula.toString() << std::endl;
storm::storage::BitVector result;
try {
result = ltlFormula.check(*this);
LOG4CPLUS_INFO(logger, "Result for initial states:");
std::cout << "Result for initial states:" << std::endl;
for (auto initialState : model.getInitialStates()) {
LOG4CPLUS_INFO(logger, "\t" << initialState << ": " << (result.get(initialState) ? "satisfied" : "not satisfied"));
std::cout << "\t" << initialState << ": " << result.get(initialState) << std::endl;
}
} catch (std::exception& e) {
std::cout << "Error during computation: " << e.what() << "Skipping property." << std::endl;
LOG4CPLUS_ERROR(logger, "Error during computation: " << e.what() << "Skipping property.");
}
std::cout << std::endl << "-------------------------------------------" << std::endl;
}
/*!
* Checks the given formula consisting of a single atomic proposition.
*
* @param formula The formula to be checked.
* @returns The set of states satisfying the formula represented by a bit vector.
*/
virtual std::vector<Type> checkAp(storm::property::ltl::Ap<Type> const& formula) const = 0;
virtual std::vector<Type> checkAp(storm::properties::ltl::Ap<Type> const& formula) const = 0;
/*!
* Checks the given formula that is a logical "and" of two formulae.
@ -144,7 +118,7 @@ public:
* @param formula The formula to be checked.
* @returns The set of states satisfying the formula represented by a bit vector.
*/
virtual std::vector<Type> checkAnd(storm::property::ltl::And<Type> const& formula) const = 0;
virtual std::vector<Type> checkAnd(storm::properties::ltl::And<Type> const& formula) const = 0;
/*!
* Checks the given formula that is a logical "or" of two formulae.
@ -152,7 +126,7 @@ public:
* @param formula The formula to check.
* @returns The set of states satisfying the formula represented by a bit vector.
*/
virtual std::vector<Type> checkOr(storm::property::ltl::Or<Type> const& formula) const = 0;
virtual std::vector<Type> checkOr(storm::properties::ltl::Or<Type> const& formula) const = 0;
/*!
* Checks the given formula that is a logical "not" of a sub-formula.
@ -160,7 +134,7 @@ public:
* @param formula The formula to check.
* @returns The set of states satisfying the formula represented by a bit vector.
*/
virtual std::vector<Type> checkNot(const storm::property::ltl::Not<Type>& formula) const = 0;
virtual std::vector<Type> checkNot(const storm::properties::ltl::Not<Type>& formula) const = 0;
private:

181
src/modelchecker/prctl/AbstractModelChecker.h

@ -17,8 +17,9 @@ namespace prctl {
}
}
#include <stack>
#include "src/exceptions/InvalidPropertyException.h"
#include "src/formula/Prctl.h"
#include "src/properties/Prctl.h"
#include "src/storage/BitVector.h"
#include "src/models/AbstractModel.h"
#include "src/settings/Settings.h"
@ -46,35 +47,34 @@ template<class Type>
class AbstractModelChecker :
// A list of interfaces the model checker supports. Typically, for each of the interfaces, a check method needs to
// be implemented that performs the corresponding check.
public virtual storm::property::prctl::IApModelChecker<Type>,
public virtual storm::property::prctl::IAndModelChecker<Type>,
public virtual storm::property::prctl::IOrModelChecker<Type>,
public virtual storm::property::prctl::INotModelChecker<Type>,
public virtual storm::property::prctl::IUntilModelChecker<Type>,
public virtual storm::property::prctl::IEventuallyModelChecker<Type>,
public virtual storm::property::prctl::IGloballyModelChecker<Type>,
public virtual storm::property::prctl::INextModelChecker<Type>,
public virtual storm::property::prctl::IBoundedUntilModelChecker<Type>,
public virtual storm::property::prctl::IBoundedEventuallyModelChecker<Type>,
public virtual storm::property::prctl::INoBoundOperatorModelChecker<Type>,
public virtual storm::property::prctl::IProbabilisticBoundOperatorModelChecker<Type>,
public virtual storm::property::prctl::IRewardBoundOperatorModelChecker<Type>,
public virtual storm::property::prctl::IReachabilityRewardModelChecker<Type>,
public virtual storm::property::prctl::ICumulativeRewardModelChecker<Type>,
public virtual storm::property::prctl::IInstantaneousRewardModelChecker<Type> {
public virtual storm::properties::prctl::IApModelChecker<Type>,
public virtual storm::properties::prctl::IAndModelChecker<Type>,
public virtual storm::properties::prctl::IOrModelChecker<Type>,
public virtual storm::properties::prctl::INotModelChecker<Type>,
public virtual storm::properties::prctl::IUntilModelChecker<Type>,
public virtual storm::properties::prctl::IEventuallyModelChecker<Type>,
public virtual storm::properties::prctl::IGloballyModelChecker<Type>,
public virtual storm::properties::prctl::INextModelChecker<Type>,
public virtual storm::properties::prctl::IBoundedUntilModelChecker<Type>,
public virtual storm::properties::prctl::IBoundedEventuallyModelChecker<Type>,
public virtual storm::properties::prctl::IProbabilisticBoundOperatorModelChecker<Type>,
public virtual storm::properties::prctl::IRewardBoundOperatorModelChecker<Type>,
public virtual storm::properties::prctl::IReachabilityRewardModelChecker<Type>,
public virtual storm::properties::prctl::ICumulativeRewardModelChecker<Type>,
public virtual storm::properties::prctl::IInstantaneousRewardModelChecker<Type> {
public:
/*!
* Constructs an AbstractModelChecker with the given model.
*/
explicit AbstractModelChecker(storm::models::AbstractModel<Type> const& model) : model(model){
explicit AbstractModelChecker(storm::models::AbstractModel<Type> const& model) : minimumOperatorStack(), model(model) {
// Intentionally left empty.
}
/*!
* Copy constructs an AbstractModelChecker from the given model checker. In particular, this means that the newly
* constructed model checker will have the model of the given model checker as its associated model.
*/
explicit AbstractModelChecker(AbstractModelChecker<Type> const& modelchecker) : model(modelchecker.model) {
explicit AbstractModelChecker(AbstractModelChecker<Type> const& modelchecker) : minimumOperatorStack(), model(modelchecker.model) {
// Intentionally left empty.
}
@ -120,73 +120,6 @@ public:
throw bc;
}
}
/*!
* Checks the given abstract prctl formula on the model and prints the result (depending on the actual type of the formula)
* for all initial states, i.e. states that carry the atomic proposition "init".
*
* @param formula The formula to be checked.
*/
void check(storm::property::prctl::AbstractPrctlFormula<Type> const& formula) const {
if (dynamic_cast<storm::property::prctl::AbstractStateFormula<Type> const*>(&formula) != nullptr) {
this->check(static_cast<storm::property::prctl::AbstractStateFormula<Type> const&>(formula));
} else if (dynamic_cast<storm::property::prctl::AbstractNoBoundOperator<Type> const*>(&formula) != nullptr) {
this->check(static_cast<storm::property::prctl::AbstractNoBoundOperator<Type> const&>(formula));
}
}
/*!
* Checks the given state formula on the model and prints the result (true/false) for all initial states, i.e.
* states that carry the atomic proposition "init".
*
* @param stateFormula The formula to be checked.
*/
void check(storm::property::prctl::AbstractStateFormula<Type> const& stateFormula) const {
std::cout << std::endl;
LOG4CPLUS_INFO(logger, "Model checking formula\t" << stateFormula.toString());
std::cout << "Model checking formula:\t" << stateFormula.toString() << std::endl;
storm::storage::BitVector result;
try {
result = stateFormula.check(*this);
LOG4CPLUS_INFO(logger, "Result for initial states:");
std::cout << "Result for initial states:" << std::endl;
for (auto initialState : model.getInitialStates()) {
LOG4CPLUS_INFO(logger, "\t" << initialState << ": " << (result.get(initialState) ? "satisfied" : "not satisfied"));
std::cout << "\t" << initialState << ": " << result.get(initialState) << std::endl;
}
} catch (std::exception& e) {
std::cout << "Error during computation: " << e.what() << "Skipping property." << std::endl;
LOG4CPLUS_ERROR(logger, "Error during computation: " << e.what() << "Skipping property.");
}
std::cout << std::endl << "-------------------------------------------" << std::endl;
}
/*!
* Checks the given formula (with no bound) on the model and prints the result (probability/rewards) for all
* initial states, i.e. states that carry the atomic proposition "init".
*
* @param noBoundFormula The formula to be checked.
*/
void check(storm::property::prctl::AbstractNoBoundOperator<Type> const& noBoundFormula) const {
std::cout << std::endl;
LOG4CPLUS_INFO(logger, "Model checking formula\t" << noBoundFormula.toString());
std::cout << "Model checking formula:\t" << noBoundFormula.toString() << std::endl;
std::vector<Type> result;
try {
result = this->checkNoBoundOperator(noBoundFormula);
LOG4CPLUS_INFO(logger, "Result for initial states:");
std::cout << "Result for initial states:" << std::endl;
for (auto initialState : model.getInitialStates()) {
LOG4CPLUS_INFO(logger, "\t" << initialState << ": " << result[initialState]);
std::cout << "\t" << initialState << ": " << result[initialState] << std::endl;
}
} catch (std::exception& e) {
std::cout << "Error during computation: " << e.what() << " Skipping property." << std::endl;
LOG4CPLUS_ERROR(logger, "Error during computation: " << e.what() << "Skipping property.");
}
std::cout << std::endl << "-------------------------------------------" << std::endl;
}
/*!
* Checks the given formula consisting of a single atomic proposition.
@ -194,7 +127,7 @@ public:
* @param formula The formula to be checked.
* @return The set of states satisfying the formula represented by a bit vector.
*/
storm::storage::BitVector checkAp(storm::property::prctl::Ap<Type> const& formula) const {
storm::storage::BitVector checkAp(storm::properties::prctl::Ap<Type> const& formula) const {
if (formula.getAp() == "true") {
return storm::storage::BitVector(model.getNumberOfStates(), true);
} else if (formula.getAp() == "false") {
@ -215,9 +148,9 @@ public:
* @param formula The formula to be checked.
* @return The set of states satisfying the formula represented by a bit vector.
*/
storm::storage::BitVector checkAnd(storm::property::prctl::And<Type> const& formula) const {
storm::storage::BitVector result = formula.getLeft().check(*this);
storm::storage::BitVector right = formula.getRight().check(*this);
storm::storage::BitVector checkAnd(storm::properties::prctl::And<Type> const& formula) const {
storm::storage::BitVector result = formula.getLeft()->check(*this);
storm::storage::BitVector right = formula.getRight()->check(*this);
result &= right;
return result;
}
@ -228,9 +161,9 @@ public:
* @param formula The formula to check.
* @return The set of states satisfying the formula represented by a bit vector.
*/
storm::storage::BitVector checkOr(storm::property::prctl::Or<Type> const& formula) const {
storm::storage::BitVector result = formula.getLeft().check(*this);
storm::storage::BitVector right = formula.getRight().check(*this);
storm::storage::BitVector checkOr(storm::properties::prctl::Or<Type> const& formula) const {
storm::storage::BitVector result = formula.getLeft()->check(*this);
storm::storage::BitVector right = formula.getRight()->check(*this);
result |= right;
return result;
}
@ -241,8 +174,8 @@ public:
* @param formula The formula to check.
* @return The set of states satisfying the formula represented by a bit vector.
*/
storm::storage::BitVector checkNot(const storm::property::prctl::Not<Type>& formula) const {
storm::storage::BitVector result = formula.getChild().check(*this);
storm::storage::BitVector checkNot(const storm::properties::prctl::Not<Type>& formula) const {
storm::storage::BitVector result = formula.getChild()->check(*this);
result.complement();
return result;
}
@ -254,9 +187,9 @@ public:
* @param formula The formula to check.
* @return The set of states satisfying the formula represented by a bit vector.
*/
storm::storage::BitVector checkProbabilisticBoundOperator(storm::property::prctl::ProbabilisticBoundOperator<Type> const& formula) const {
virtual storm::storage::BitVector checkProbabilisticBoundOperator(storm::properties::prctl::ProbabilisticBoundOperator<Type> const& formula) const {
// First, we need to compute the probability for satisfying the path formula for each state.
std::vector<Type> quantitativeResult = formula.getPathFormula().check(*this, false);
std::vector<Type> quantitativeResult = formula.getChild()->check(*this, false);
// Create resulting bit vector that will hold the yes/no-answer for every state.
storm::storage::BitVector result(quantitativeResult.size());
@ -278,9 +211,9 @@ public:
* @param formula The formula to check.
* @return The set of states satisfying the formula represented by a bit vector.
*/
storm::storage::BitVector checkRewardBoundOperator(const storm::property::prctl::RewardBoundOperator<Type>& formula) const {
virtual storm::storage::BitVector checkRewardBoundOperator(const storm::properties::prctl::RewardBoundOperator<Type>& formula) const {
// First, we need to compute the probability for satisfying the path formula for each state.
std::vector<Type> quantitativeResult = formula.getPathFormula().check(*this, false);
std::vector<Type> quantitativeResult = formula.getChild()->check(*this, false);
// Create resulting bit vector that will hold the yes/no-answer for every state.
storm::storage::BitVector result(quantitativeResult.size());
@ -296,6 +229,56 @@ public:
return result;
}
/*!
* Checks the given formula and determines whether minimum or maximum probabilities are to be computed for the formula.
*
* @param formula The formula to check.
* @param optOperator True iff minimum probabilities are to be computed.
* @returns The probabilities to satisfy the formula, represented by a vector.
*/
virtual std::vector<Type> checkOptimizingOperator(storm::properties::prctl::AbstractPathFormula<Type> const & formula, bool optOperator) const {
minimumOperatorStack.push(optOperator);
std::vector<Type> result = formula.check(*this, false);
minimumOperatorStack.pop();
return result;
}
/*!
* Checks the given formula and determines whether minimum or maximum rewards are to be computed for the formula.
*
* @param formula The formula to check.
* @param optOperator True iff minimum rewards are to be computed.
* @returns The the rewards accumulated by the formula, represented by a vector.
*/
virtual std::vector<Type> checkOptimizingOperator(storm::properties::prctl::AbstractRewardPathFormula<Type> const & formula, bool optOperator) const {
minimumOperatorStack.push(optOperator);
std::vector<Type> result = formula.check(*this, false);
minimumOperatorStack.pop();
return result;
}
/*!
* Checks the given formula and determines whether minimum or maximum probabilities or rewards are to be computed for the formula.
*
* @param formula The formula to check.
* @param optOperator True iff minimum probabilities/rewards are to be computed.
* @returns The set of states satisfying the formula represented by a bit vector.
*/
virtual storm::storage::BitVector checkOptimizingOperator(storm::properties::prctl::AbstractStateFormula<Type> const & formula, bool optOperator) const {
minimumOperatorStack.push(optOperator);
storm::storage::BitVector result = formula.check(*this);
minimumOperatorStack.pop();
return result;
}
protected:
/*!
* A stack used for storing whether we are currently computing min or max probabilities or rewards, respectively.
* The topmost element is true if and only if we are currently computing minimum probabilities or rewards.
*/
mutable std::stack<bool> minimumOperatorStack;
private:
/*!

83
src/modelchecker/prctl/SparseDtmcPrctlModelChecker.h

@ -60,21 +60,6 @@ public:
return AbstractModelChecker<Type>::template getModel<storm::models::Dtmc<Type>>();
}
/*!
* Checks the given formula that is a P/R operator without a bound.
*
* @param formula The formula to check.
* @returns The set of states satisfying the formula represented by a bit vector.
*/
std::vector<Type> checkNoBoundOperator(storm::property::prctl::AbstractNoBoundOperator<Type> const& formula) const {
// Check if the operator was an optimality operator and report a warning in that case.
if (formula.isOptimalityOperator()) {
LOG4CPLUS_WARN(logger, "Formula contains min/max operator, which is not meaningful over deterministic models.");
}
return formula.check(*this, false);
}
/*!
* Checks the given formula that is a bounded-until formula.
*
@ -86,8 +71,8 @@ public:
* @returns The probabilities for the given formula to hold on every state of the model associated with this model
* checker. If the qualitative flag is set, exact probabilities might not be computed.
*/
virtual std::vector<Type> checkBoundedUntil(storm::property::prctl::BoundedUntil<Type> const& formula, bool qualitative) const {
return this->checkBoundedUntil(formula.getLeft().check(*this), formula.getRight().check(*this), formula.getBound(), qualitative);
virtual std::vector<Type> checkBoundedUntil(storm::properties::prctl::BoundedUntil<Type> const& formula, bool qualitative) const {
return this->checkBoundedUntil(formula.getLeft()->check(*this), formula.getRight()->check(*this), formula.getBound(), qualitative);
}
/*!
@ -160,9 +145,9 @@ public:
* @returns The probabilities for the given formula to hold on every state of the model associated with this model
* checker. If the qualitative flag is set, exact probabilities might not be computed.
*/
virtual std::vector<Type> checkNext(storm::property::prctl::Next<Type> const& formula, bool qualitative) const {
virtual std::vector<Type> checkNext(storm::properties::prctl::Next<Type> const& formula, bool qualitative) const {
// First, we need to compute the states that satisfy the child formula of the next-formula.
storm::storage::BitVector nextStates = formula.getChild().check(*this);
storm::storage::BitVector nextStates = formula.getChild()->check(*this);
// Create the vector with which to multiply and initialize it correctly.
std::vector<Type> result(this->getModel().getNumberOfStates());
@ -189,8 +174,8 @@ public:
* @returns The probabilities for the given formula to hold on every state of the model associated with this model
* checker. If the qualitative flag is set, exact probabilities might not be computed.
*/
virtual std::vector<Type> checkBoundedEventually(storm::property::prctl::BoundedEventually<Type> const& formula, bool qualitative) const {
return this->checkBoundedUntil(storm::storage::BitVector(this->getModel().getNumberOfStates(), true), formula.getChild().check(*this), formula.getBound(), qualitative);
virtual std::vector<Type> checkBoundedEventually(storm::properties::prctl::BoundedEventually<Type> const& formula, bool qualitative) const {
return this->checkBoundedUntil(storm::storage::BitVector(this->getModel().getNumberOfStates(), true), formula.getChild()->check(*this), formula.getBound(), qualitative);
}
/*!
@ -204,9 +189,9 @@ public:
* @returns The probabilities for the given formula to hold on every state of the model associated with this model
* checker. If the qualitative flag is set, exact probabilities might not be computed.
*/
virtual std::vector<Type> checkEventually(storm::property::prctl::Eventually<Type> const& formula, bool qualitative) const {
virtual std::vector<Type> checkEventually(storm::properties::prctl::Eventually<Type> const& formula, bool qualitative) const {
// Create equivalent temporary until formula and check it.
storm::property::prctl::Until<Type> temporaryUntilFormula(new storm::property::prctl::Ap<Type>("true"), formula.getChild().clone());
storm::properties::prctl::Until<Type> temporaryUntilFormula(std::shared_ptr<storm::properties::prctl::Ap<Type>>(new storm::properties::prctl::Ap<Type>("true")), formula.getChild());
return this->checkUntil(temporaryUntilFormula, qualitative);
}
@ -221,9 +206,9 @@ public:
* @returns The probabilities for the given formula to hold on every state of the model associated with this model
* checker. If the qualitative flag is set, exact probabilities might not be computed.
*/
virtual std::vector<Type> checkGlobally(storm::property::prctl::Globally<Type> const& formula, bool qualitative) const {
virtual std::vector<Type> checkGlobally(storm::properties::prctl::Globally<Type> const& formula, bool qualitative) const {
// Create "equivalent" (equivalent up to negation) temporary eventually formula and check it.
storm::property::prctl::Eventually<Type> temporaryEventuallyFormula(new storm::property::prctl::Not<Type>(formula.getChild().clone()));
storm::properties::prctl::Eventually<Type> temporaryEventuallyFormula(std::shared_ptr<storm::properties::prctl::Not<Type>>(new storm::properties::prctl::Not<Type>(formula.getChild())));
std::vector<Type> result = this->checkEventually(temporaryEventuallyFormula, qualitative);
// Now subtract the resulting vector from the constant one vector to obtain final result.
@ -243,8 +228,8 @@ public:
* @returns The probabilities for the given formula to hold on every state of the model associated with this model
* checker. If the qualitative flag is set, exact probabilities might not be computed.
*/
virtual std::vector<Type> checkUntil(storm::property::prctl::Until<Type> const& formula, bool qualitative) const {
return this->checkUntil(formula.getLeft().check(*this), formula.getRight().check(*this), qualitative);
virtual std::vector<Type> checkUntil(storm::properties::prctl::Until<Type> const& formula, bool qualitative) const {
return this->checkUntil(formula.getLeft()->check(*this), formula.getRight()->check(*this), qualitative);
}
/*!
@ -334,7 +319,7 @@ public:
* @returns The reward values for the given formula for every state of the model associated with this model
* checker. If the qualitative flag is set, exact values might not be computed.
*/
virtual std::vector<Type> checkInstantaneousReward(storm::property::prctl::InstantaneousReward<Type> const& formula, bool qualitative) const {
virtual std::vector<Type> checkInstantaneousReward(storm::properties::prctl::InstantaneousReward<Type> const& formula, bool qualitative) const {
// Only compute the result if the model has a state-based reward model.
if (!this->getModel().hasStateRewards()) {
LOG4CPLUS_ERROR(logger, "Missing (state-based) reward model for formula.");
@ -365,7 +350,7 @@ public:
* @returns The reward values for the given formula for every state of the model associated with this model
* checker. If the qualitative flag is set, exact values might not be computed.
*/
virtual std::vector<Type> checkCumulativeReward(storm::property::prctl::CumulativeReward<Type> const& formula, bool qualitative) const {
virtual std::vector<Type> checkCumulativeReward(storm::properties::prctl::CumulativeReward<Type> const& formula, bool qualitative) const {
// Only compute the result if the model has at least one reward model.
if (!this->getModel().hasStateRewards() && !this->getModel().hasTransitionRewards()) {
LOG4CPLUS_ERROR(logger, "Missing reward model for formula.");
@ -412,7 +397,7 @@ public:
* @returns The reward values for the given formula for every state of the model associated with this model
* checker. If the qualitative flag is set, exact values might not be computed.
*/
virtual std::vector<Type> checkReachabilityReward(storm::property::prctl::ReachabilityReward<Type> const& formula, bool qualitative) const {
virtual std::vector<Type> checkReachabilityReward(storm::properties::prctl::ReachabilityReward<Type> const& formula, bool qualitative) const {
// Only compute the result if the model has at least one reward model.
if (!this->getModel().hasStateRewards() && !this->getModel().hasTransitionRewards()) {
LOG4CPLUS_ERROR(logger, "Missing reward model for formula. Skipping formula");
@ -420,7 +405,7 @@ public:
}
// Determine the states for which the target predicate holds.
storm::storage::BitVector targetStates = formula.getChild().check(*this);
storm::storage::BitVector targetStates = formula.getChild()->check(*this);
// Determine which states have a reward of infinity by definition.
storm::storage::BitVector trueStates(this->getModel().getNumberOfStates(), true);
@ -497,6 +482,42 @@ public:
return result;
}
/*!
* Checks the given formula.
* @note This methods overrides the method of the base class to give an additional warning that declaring that minimal or maximal probabilities
* should be computed for the formula makes no sense in the context of a deterministic model.
*
* @param formula The formula to check.
* @param optOperator True iff minimum probabilities/rewards are to be computed.
* @returns The probabilities to satisfy the formula or the rewards accumulated by it, represented by a vector.
*/
virtual std::vector<Type> checkOptimizingOperator(storm::properties::prctl::AbstractPathFormula<Type> const & formula, bool optOperator) const override {
LOG4CPLUS_WARN(logger, "Formula contains min/max operator, which is not meaningful over deterministic models.");
std::vector<Type> result = formula.check(*this, false);
return result;
}
/*!
* Checks the given formula and determines whether minimum or maximum probabilities or rewards are to be computed for the formula.
* @note This methods overrides the method of the base class to give an additional warning that declaring that minimal or maximal probabilities
* should be computed for the formula makes no sense in the context of a deterministic model.
*
* @param formula The formula to check.
* @param optOperator True iff minimum probabilities/rewards are to be computed.
* @returns The set of states satisfying the formula represented by a bit vector.
*/
virtual storm::storage::BitVector checkOptimizingOperator(storm::properties::prctl::AbstractStateFormula<Type> const & formula, bool optOperator) const override {
LOG4CPLUS_WARN(logger, "Formula contains min/max operator, which is not meaningful over deterministic models.");
storm::storage::BitVector result = formula.check(*this);
return result;
}
private:
// An object that is used for solving linear equations and performing matrix-vector multiplication.
std::unique_ptr<storm::solver::LinearEquationSolver<Type>> linearEquationSolver;

192
src/modelchecker/prctl/SparseMdpPrctlModelChecker.h

@ -9,7 +9,6 @@
#define STORM_MODELCHECKER_PRCTL_SPARSEMDPPRCTLMODELCHECKER_H_
#include <vector>
#include <stack>
#include <fstream>
#include "src/modelchecker/prctl/AbstractModelChecker.h"
@ -38,11 +37,11 @@ namespace storm {
*
* @param model The MDP to be checked.
*/
explicit SparseMdpPrctlModelChecker(storm::models::Mdp<Type> const& model) : AbstractModelChecker<Type>(model), minimumOperatorStack(), nondeterministicLinearEquationSolver(storm::utility::solver::getNondeterministicLinearEquationSolver<Type>()) {
explicit SparseMdpPrctlModelChecker(storm::models::Mdp<Type> const& model) : AbstractModelChecker<Type>(model), nondeterministicLinearEquationSolver(storm::utility::solver::getNondeterministicLinearEquationSolver<Type>()) {
// Intentionally left empty.
}
explicit SparseMdpPrctlModelChecker(storm::models::Mdp<Type> const& model, std::shared_ptr<storm::solver::NondeterministicLinearEquationSolver<Type>> nondeterministicLinearEquationSolver) : AbstractModelChecker<Type>(model), minimumOperatorStack(), nondeterministicLinearEquationSolver(nondeterministicLinearEquationSolver) {
explicit SparseMdpPrctlModelChecker(storm::models::Mdp<Type> const& model, std::shared_ptr<storm::solver::NondeterministicLinearEquationSolver<Type>> nondeterministicLinearEquationSolver) : AbstractModelChecker<Type>(model), nondeterministicLinearEquationSolver(nondeterministicLinearEquationSolver) {
// Intentionally left empty.
}
@ -51,10 +50,17 @@ namespace storm {
* constructed model checker will have the model of the given model checker as its associated model.
*/
explicit SparseMdpPrctlModelChecker(storm::modelchecker::prctl::SparseMdpPrctlModelChecker<Type> const& modelchecker)
: AbstractModelChecker<Type>(modelchecker), minimumOperatorStack(), nondeterministicLinearEquationSolver(storm::utility::solver::getNondeterministicLinearEquationSolver<Type>()) {
: AbstractModelChecker<Type>(modelchecker), nondeterministicLinearEquationSolver(storm::utility::solver::getNondeterministicLinearEquationSolver<Type>()) {
// Intentionally left empty.
}
/*!
* Virtual destructor. Needs to be virtual, because this class has virtual methods.
*/
virtual ~SparseMdpPrctlModelChecker() {
// Intentionally left empty.
}
/*!
* Returns a constant reference to the MDP associated with this model checker.
* @returns A constant reference to the MDP associated with this model checker.
@ -62,25 +68,81 @@ namespace storm {
storm::models::Mdp<Type> const& getModel() const {
return AbstractModelChecker<Type>::template getModel<storm::models::Mdp<Type>>();
}
/*!
* Checks the given formula that is a P/R operator without a bound.
*
* @param formula The formula to check.
* @returns The set of states satisfying the formula represented by a bit vector.
*/
virtual std::vector<Type> checkNoBoundOperator(const storm::property::prctl::AbstractNoBoundOperator<Type>& formula) const {
// Check if the operator was an non-optimality operator and report an error in that case.
if (!formula.isOptimalityOperator()) {
LOG4CPLUS_ERROR(logger, "Formula does not specify neither min nor max optimality, which is not meaningful over nondeterministic models.");
throw storm::exceptions::InvalidArgumentException() << "Formula does not specify neither min nor max optimality, which is not meaningful over nondeterministic models.";
}
minimumOperatorStack.push(formula.isMinimumOperator());
std::vector<Type> result = formula.check(*this, false);
minimumOperatorStack.pop();
return result;
}
/*!
* Checks the given formula that is a P operator over a path formula featuring a value bound.
*
* @param formula The formula to check.
* @return The set of states satisfying the formula represented by a bit vector.
*/
virtual storm::storage::BitVector checkProbabilisticBoundOperator(storm::properties::prctl::ProbabilisticBoundOperator<Type> const& formula) const override {
// For P< and P<= the MDP satisfies the formula iff the probability maximizing scheduler is used.
// For P> and P>= " iff the probability minimizing " .
if(formula.getComparisonOperator() == storm::properties::LESS || formula.getComparisonOperator() == storm::properties::LESS_EQUAL) {
this->minimumOperatorStack.push(false);
}
else {
this->minimumOperatorStack.push(true);
}
// First, we need to compute the probability for satisfying the path formula for each state.
std::vector<Type> quantitativeResult = formula.getChild()->check(*this, false);
//Remove the minimizing operator entry from the stack.
this->minimumOperatorStack.pop();
// Create resulting bit vector that will hold the yes/no-answer for every state.
storm::storage::BitVector result(quantitativeResult.size());
// Now, we can compute which states meet the bound specified in this operator and set the
// corresponding bits to true in the resulting vector.
for (uint_fast64_t i = 0; i < quantitativeResult.size(); ++i) {
if (formula.meetsBound(quantitativeResult[i])) {
result.set(i, true);
}
}
return result;
}
/*!
* Checks the given formula that is an R operator over a reward formula featuring a value bound.
*
* @param formula The formula to check.
* @return The set of states satisfying the formula represented by a bit vector.
*/
virtual storm::storage::BitVector checkRewardBoundOperator(const storm::properties::prctl::RewardBoundOperator<Type>& formula) const override {
// For R< and R<= the MDP satisfies the formula iff the reward maximizing scheduler is used.
// For R> and R>= " iff the reward minimizing " .
if(formula.getComparisonOperator() == storm::properties::LESS || formula.getComparisonOperator() == storm::properties::LESS_EQUAL) {
this->minimumOperatorStack.push(false);
}
else {
this->minimumOperatorStack.push(true);
}
// First, we need to compute the probability for satisfying the path formula for each state.
std::vector<Type> quantitativeResult = formula.getChild()->check(*this, false);
//Remove the minimizing operator entry from the stack.
this->minimumOperatorStack.pop();
// Create resulting bit vector that will hold the yes/no-answer for every state.
storm::storage::BitVector result(quantitativeResult.size());
// Now, we can compute which states meet the bound specified in this operator and set the
// corresponding bits to true in the resulting vector.
for (uint_fast64_t i = 0; i < quantitativeResult.size(); ++i) {
if (formula.meetsBound(quantitativeResult[i])) {
result.set(i, true);
}
}
return result;
}
/*!
* Computes the probability to satisfy phi until psi within a limited number of steps for each state.
*
@ -95,7 +157,13 @@ namespace storm {
* If the qualitative flag is set, exact probabilities might not be computed.
*/
std::vector<Type> checkBoundedUntil(storm::storage::BitVector const& phiStates, storm::storage::BitVector const& psiStates, uint_fast64_t stepBound, bool qualitative) const {
std::vector<Type> result(this->getModel().getNumberOfStates());
// First test if it is specified if the minimum or maximum probabilities are to be computed.
if(this->minimumOperatorStack.empty()) {
LOG4CPLUS_ERROR(logger, "Formula does not specify neither min nor max optimality, which is not meaningful over nondeterministic models.");
throw storm::exceptions::InvalidArgumentException() << "Formula does not specify neither min nor max optimality, which is not meaningful over nondeterministic models.";
}
std::vector<Type> result(this->getModel().getNumberOfStates());
// Determine the states that have 0 probability of reaching the target states.
storm::storage::BitVector statesWithProbabilityGreater0;
@ -150,8 +218,8 @@ namespace storm {
* @return The probabilities for the given formula to hold on every state of the model associated with this model
* checker. If the qualitative flag is set, exact probabilities might not be computed.
*/
virtual std::vector<Type> checkBoundedUntil(storm::property::prctl::BoundedUntil<Type> const& formula, bool qualitative) const {
return checkBoundedUntil(formula.getLeft().check(*this), formula.getRight().check(*this), formula.getBound(), qualitative);
virtual std::vector<Type> checkBoundedUntil(storm::properties::prctl::BoundedUntil<Type> const& formula, bool qualitative) const {
return checkBoundedUntil(formula.getLeft()->check(*this), formula.getRight()->check(*this), formula.getBound(), qualitative);
}
/*!
@ -166,6 +234,12 @@ namespace storm {
* qualitative flag is set, exact probabilities might not be computed.
*/
virtual std::vector<Type> checkNext(storm::storage::BitVector const& nextStates, bool qualitative) const {
// First test if it is specified if the minimum or maximum probabilities are to be computed.
if(this->minimumOperatorStack.empty()) {
LOG4CPLUS_ERROR(logger, "Formula does not specify neither min nor max optimality, which is not meaningful over nondeterministic models.");
throw storm::exceptions::InvalidArgumentException() << "Formula does not specify neither min nor max optimality, which is not meaningful over nondeterministic models.";
}
// Create the vector with which to multiply and initialize it correctly.
std::vector<Type> result(this->getModel().getNumberOfStates());
storm::utility::vector::setVectorValues(result, nextStates, storm::utility::constantOne<Type>());
@ -186,8 +260,8 @@ namespace storm {
* @return The probabilities for the given formula to hold on every state of the model associated with this model
* checker. If the qualitative flag is set, exact probabilities might not be computed.
*/
virtual std::vector<Type> checkNext(const storm::property::prctl::Next<Type>& formula, bool qualitative) const {
return checkNext(formula.getChild().check(*this), qualitative);
virtual std::vector<Type> checkNext(const storm::properties::prctl::Next<Type>& formula, bool qualitative) const {
return checkNext(formula.getChild()->check(*this), qualitative);
}
/*!
@ -201,9 +275,9 @@ namespace storm {
* @returns The probabilities for the given formula to hold on every state of the model associated with this model
* checker. If the qualitative flag is set, exact probabilities might not be computed.
*/
virtual std::vector<Type> checkBoundedEventually(const storm::property::prctl::BoundedEventually<Type>& formula, bool qualitative) const {
virtual std::vector<Type> checkBoundedEventually(const storm::properties::prctl::BoundedEventually<Type>& formula, bool qualitative) const {
// Create equivalent temporary bounded until formula and check it.
storm::property::prctl::BoundedUntil<Type> temporaryBoundedUntilFormula(new storm::property::prctl::Ap<Type>("true"), formula.getChild().clone(), formula.getBound());
storm::properties::prctl::BoundedUntil<Type> temporaryBoundedUntilFormula(std::shared_ptr<storm::properties::prctl::Ap<Type>>(new storm::properties::prctl::Ap<Type>("true")), formula.getChild(), formula.getBound());
return this->checkBoundedUntil(temporaryBoundedUntilFormula, qualitative);
}
@ -218,9 +292,9 @@ namespace storm {
* @returns The probabilities for the given formula to hold on every state of the model associated with this model
* checker. If the qualitative flag is set, exact probabilities might not be computed.
*/
virtual std::vector<Type> checkEventually(const storm::property::prctl::Eventually<Type>& formula, bool qualitative) const {
virtual std::vector<Type> checkEventually(const storm::properties::prctl::Eventually<Type>& formula, bool qualitative) const {
// Create equivalent temporary until formula and check it.
storm::property::prctl::Until<Type> temporaryUntilFormula(new storm::property::prctl::Ap<Type>("true"), formula.getChild().clone());
storm::properties::prctl::Until<Type> temporaryUntilFormula(std::shared_ptr<storm::properties::prctl::Ap<Type>>(new storm::properties::prctl::Ap<Type>("true")), formula.getChild());
return this->checkUntil(temporaryUntilFormula, qualitative);
}
@ -235,9 +309,9 @@ namespace storm {
* @returns The probabilities for the given formula to hold on every state of the model associated with this model
* checker. If the qualitative flag is set, exact probabilities might not be computed.
*/
virtual std::vector<Type> checkGlobally(const storm::property::prctl::Globally<Type>& formula, bool qualitative) const {
virtual std::vector<Type> checkGlobally(const storm::properties::prctl::Globally<Type>& formula, bool qualitative) const {
// Create "equivalent" temporary eventually formula and check it.
storm::property::prctl::Eventually<Type> temporaryEventuallyFormula(new storm::property::prctl::Not<Type>(formula.getChild().clone()));
storm::properties::prctl::Eventually<Type> temporaryEventuallyFormula(std::shared_ptr<storm::properties::prctl::Not<Type>>(new storm::properties::prctl::Not<Type>(formula.getChild())));
std::vector<Type> result = this->checkEventually(temporaryEventuallyFormula, qualitative);
// Now subtract the resulting vector from the constant one vector to obtain final result.
@ -259,8 +333,14 @@ namespace storm {
* @return The probabilities for the given formula to hold on every state of the model associated with this model
* checker. If the qualitative flag is set, exact probabilities might not be computed.
*/
virtual std::vector<Type> checkUntil(const storm::property::prctl::Until<Type>& formula, bool qualitative) const {
return this->checkUntil(this->minimumOperatorStack.top(), formula.getLeft().check(*this), formula.getRight().check(*this), qualitative).first;
virtual std::vector<Type> checkUntil(const storm::properties::prctl::Until<Type>& formula, bool qualitative) const {
// First test if it is specified if the minimum or maximum probabilities are to be computed.
if(this->minimumOperatorStack.empty()) {
LOG4CPLUS_ERROR(logger, "Formula does not specify neither min nor max optimality, which is not meaningful over nondeterministic models.");
throw storm::exceptions::InvalidArgumentException() << "Formula does not specify neither min nor max optimality, which is not meaningful over nondeterministic models.";
}
return this->checkUntil(this->minimumOperatorStack.top(), formula.getLeft()->check(*this), formula.getRight()->check(*this), qualitative).first;
}
/*!
@ -358,13 +438,19 @@ namespace storm {
* @return The reward values for the given formula for every state of the model associated with this model
* checker. If the qualitative flag is set, exact values might not be computed.
*/
virtual std::vector<Type> checkInstantaneousReward(const storm::property::prctl::InstantaneousReward<Type>& formula, bool qualitative) const {
virtual std::vector<Type> checkInstantaneousReward(const storm::properties::prctl::InstantaneousReward<Type>& formula, bool qualitative) const {
// Only compute the result if the model has a state-based reward model.
if (!this->getModel().hasStateRewards()) {
LOG4CPLUS_ERROR(logger, "Missing (state-based) reward model for formula.");
throw storm::exceptions::InvalidPropertyException() << "Missing (state-based) reward model for formula.";
}
// Now test whether it is specified if the minimum or maximum probabilities are to be computed.
if(this->minimumOperatorStack.empty()) {
LOG4CPLUS_ERROR(logger, "Formula does not specify neither min nor max optimality, which is not meaningful over nondeterministic models.");
throw storm::exceptions::InvalidArgumentException() << "Formula does not specify neither min nor max optimality, which is not meaningful over nondeterministic models.";
}
// Initialize result to state rewards of the model.
std::vector<Type> result(this->getModel().getStateRewardVector());
@ -384,13 +470,19 @@ namespace storm {
* @return The reward values for the given formula for every state of the model associated with this model
* checker. If the qualitative flag is set, exact values might not be computed.
*/
virtual std::vector<Type> checkCumulativeReward(const storm::property::prctl::CumulativeReward<Type>& formula, bool qualitative) const {
virtual std::vector<Type> checkCumulativeReward(const storm::properties::prctl::CumulativeReward<Type>& formula, bool qualitative) const {
// Only compute the result if the model has at least one reward model.
if (!this->getModel().hasStateRewards() && !this->getModel().hasTransitionRewards()) {
LOG4CPLUS_ERROR(logger, "Missing reward model for formula.");
throw storm::exceptions::InvalidPropertyException() << "Missing reward model for formula.";
}
// Now test whether it is specified if the minimum or maximum probabilities are to be computed.
if(this->minimumOperatorStack.empty()) {
LOG4CPLUS_ERROR(logger, "Formula does not specify neither min nor max optimality, which is not meaningful over nondeterministic models.");
throw storm::exceptions::InvalidArgumentException() << "Formula does not specify neither min nor max optimality, which is not meaningful over nondeterministic models.";
}
// Compute the reward vector to add in each step based on the available reward models.
std::vector<Type> totalRewardVector;
if (this->getModel().hasTransitionRewards()) {
@ -426,8 +518,14 @@ namespace storm {
* @return The reward values for the given formula for every state of the model associated with this model
* checker. If the qualitative flag is set, exact values might not be computed.
*/
virtual std::vector<Type> checkReachabilityReward(const storm::property::prctl::ReachabilityReward<Type>& formula, bool qualitative) const {
return this->checkReachabilityReward(this->minimumOperatorStack.top(), formula.getChild().check(*this), qualitative).first;
virtual std::vector<Type> checkReachabilityReward(const storm::properties::prctl::ReachabilityReward<Type>& formula, bool qualitative) const {
// First test whether it is specified if the minimum or maximum probabilities are to be computed.
if(this->minimumOperatorStack.empty()) {
LOG4CPLUS_ERROR(logger, "Formula does not specify neither min nor max optimality, which is not meaningful over nondeterministic models.");
throw storm::exceptions::InvalidArgumentException() << "Formula does not specify neither min nor max optimality, which is not meaningful over nondeterministic models.";
}
return this->checkReachabilityReward(this->minimumOperatorStack.top(), formula.getChild()->check(*this), qualitative).first;
}
/*!
@ -452,6 +550,12 @@ namespace storm {
throw storm::exceptions::InvalidPropertyException() << "Missing reward model for formula.";
}
// Also test whether it is specified if the minimum or maximum probabilities are to be computed.
if(this->minimumOperatorStack.empty()) {
LOG4CPLUS_ERROR(logger, "Formula does not specify neither min nor max optimality, which is not meaningful over nondeterministic models.");
throw storm::exceptions::InvalidArgumentException() << "Formula does not specify neither min nor max optimality, which is not meaningful over nondeterministic models.";
}
// Determine which states have a reward of infinity by definition.
storm::storage::BitVector infinityStates;
storm::storage::BitVector trueStates(this->getModel().getNumberOfStates(), true);
@ -570,13 +674,7 @@ namespace storm {
return storm::storage::TotalScheduler(choices);
}
/*!
* A stack used for storing whether we are currently computing min or max probabilities or rewards, respectively.
* The topmost element is true if and only if we are currently computing minimum probabilities or rewards.
*/
mutable std::stack<bool> minimumOperatorStack;
/*!
* A solver that is used for solving systems of linear equations that are the result of nondeterministic choices.
*/

4
src/models/Dtmc.h

@ -133,7 +133,7 @@ public:
* Waring: If the vector does not have the correct size, it will be resized.
* @return The sub-Dtmc.
*/
storm::models::Dtmc<T> getSubDtmc(storm::storage::BitVector& subSysStates) {
storm::models::Dtmc<T> getSubDtmc(storm::storage::BitVector& subSysStates) const {
// Is there any state in the subsystem?
@ -159,7 +159,7 @@ public:
}
// 1. Get all necessary information from the old transition matrix
storm::storage::SparseMatrix<T> const& origMat = this->getTransitionMatrix();
storm::storage::SparseMatrix<T> const & origMat = this->getTransitionMatrix();
// Iterate over all rows. Count the number of all transitions from the old system to be
// transfered to the new one. Also build a mapping from the state number of the old system

241
src/parser/CslParser.cpp

@ -9,6 +9,14 @@
#include "src/utility/OsDetection.h"
#include "src/utility/constants.h"
// The action class headers.
#include "src/properties/actions/AbstractAction.h"
#include "src/properties/actions/BoundAction.h"
#include "src/properties/actions/InvertAction.h"
#include "src/properties/actions/FormulaAction.h"
#include "src/properties/actions/RangeAction.h"
#include "src/properties/actions/SortAction.h"
// If the parser fails due to ill-formed data, this exception is thrown.
#include "src/exceptions/WrongFormatException.h"
@ -28,25 +36,30 @@
// Some typedefs and namespace definitions to reduce code size.
#define MAKE(Type, ...) phoenix::construct<std::shared_ptr<Type>>(phoenix::new_<Type>(__VA_ARGS__))
typedef std::string::const_iterator BaseIteratorType;
typedef boost::spirit::classic::position_iterator2<BaseIteratorType> PositionIteratorType;
namespace qi = boost::spirit::qi;
namespace phoenix = boost::phoenix;
namespace csl = storm::properties::csl;
namespace storm {
namespace parser {
template<typename Iterator, typename Skipper>
struct CslGrammar : qi::grammar<Iterator, storm::property::csl::AbstractCslFormula<double>*(), Skipper > {
struct CslParser::CslGrammar : qi::grammar<Iterator, std::shared_ptr<csl::CslFilter<double>>(), Skipper > {
CslGrammar() : CslGrammar::base_type(start) {
//This block contains helper rules that may be used several times
freeIdentifierName = qi::lexeme[qi::alpha >> *(qi::alnum | qi::char_('_'))];
comparisonType = (
(qi::lit(">="))[qi::_val = storm::property::GREATER_EQUAL] |
(qi::lit(">"))[qi::_val = storm::property::GREATER] |
(qi::lit("<="))[qi::_val = storm::property::LESS_EQUAL] |
(qi::lit("<"))[qi::_val = storm::property::LESS]);
(qi::lit(">="))[qi::_val = storm::properties::GREATER_EQUAL] |
(qi::lit(">"))[qi::_val = storm::properties::GREATER] |
(qi::lit("<="))[qi::_val = storm::properties::LESS_EQUAL] |
(qi::lit("<"))[qi::_val = storm::properties::LESS]);
sortingCategory = (
(qi::lit("index"))[qi::_val = storm::properties::action::SortAction<double>::INDEX] |
(qi::lit("value"))[qi::_val = storm::properties::action::SortAction<double>::VALUE]
);
//Comment: Empty line or line starting with "//"
comment = (qi::lit("//") >> *(qi::char_))[qi::_val = nullptr];
@ -54,119 +67,179 @@ struct CslGrammar : qi::grammar<Iterator, storm::property::csl::AbstractCslFormu
stateFormula %= orFormula;
stateFormula.name("state formula");
orFormula = andFormula[qi::_val = qi::_1] > *(qi::lit("|") > andFormula)[qi::_val =
phoenix::new_<storm::property::csl::Or<double>>(qi::_val, qi::_1)];
orFormula.name("state formula");
MAKE(csl::Or<double>, qi::_val, qi::_1)];
orFormula.name("or formula");
andFormula = notFormula[qi::_val = qi::_1] > *(qi::lit("&") > notFormula)[qi::_val =
phoenix::new_<storm::property::csl::And<double>>(qi::_val, qi::_1)];
andFormula.name("state formula");
MAKE(csl::And<double>, qi::_val, qi::_1)];
andFormula.name("and formula");
notFormula = atomicStateFormula[qi::_val = qi::_1] | (qi::lit("!") > atomicStateFormula)[qi::_val =
phoenix::new_<storm::property::csl::Not<double>>(qi::_1)];
notFormula.name("state formula");
MAKE(csl::Not<double>, qi::_1)];
notFormula.name("not formula");
//This block defines rules for "atomic" state formulas
//(Propositions, probabilistic/reward formulas, and state formulas in brackets)
atomicStateFormula %= probabilisticBoundOperator | steadyStateBoundOperator | atomicProposition | qi::lit("(") >> stateFormula >> qi::lit(")");
atomicStateFormula.name("state formula");
atomicStateFormula %= probabilisticBoundOperator | steadyStateBoundOperator | atomicProposition | (qi::lit("(") >> stateFormula >> qi::lit(")")) | (qi::lit("[") >> stateFormula >> qi::lit("]"));
atomicStateFormula.name("atomic state formula");
atomicProposition = (freeIdentifierName)[qi::_val =
phoenix::new_<storm::property::csl::Ap<double>>(qi::_1)];
atomicProposition.name("state formula");
MAKE(csl::Ap<double>, qi::_1)];
atomicProposition.name("atomic proposition");
probabilisticBoundOperator = (
(qi::lit("P") >> comparisonType > qi::double_ > qi::lit("[") > pathFormula > qi::lit("]"))[qi::_val =
phoenix::new_<storm::property::csl::ProbabilisticBoundOperator<double> >(qi::_1, qi::_2, qi::_3)]
(qi::lit("P") >> comparisonType > qi::double_ > pathFormula )[qi::_val =
MAKE(csl::ProbabilisticBoundOperator<double> , qi::_1, qi::_2, qi::_3)]
);
probabilisticBoundOperator.name("state formula");
probabilisticBoundOperator.name("probabilistic bound operator");
steadyStateBoundOperator = (
(qi::lit("S") >> comparisonType > qi::double_ > qi::lit("[") > stateFormula > qi::lit("]"))[qi::_val =
phoenix::new_<storm::property::csl::SteadyStateBoundOperator<double> >(qi::_1, qi::_2, qi::_3)]
(qi::lit("S") >> comparisonType > qi::double_ > stateFormula )[qi::_val =
MAKE(csl::SteadyStateBoundOperator<double> , qi::_1, qi::_2, qi::_3)]
);
steadyStateBoundOperator.name("state formula");
//This block defines rules for parsing formulas with noBoundOperators
noBoundOperator = (probabilisticNoBoundOperator | steadyStateNoBoundOperator);
noBoundOperator.name("no bound operator");
probabilisticNoBoundOperator = (qi::lit("P") >> qi::lit("=") >> qi::lit("?") >> qi::lit("[") >> pathFormula >> qi::lit("]"))[qi::_val =
phoenix::new_<storm::property::csl::ProbabilisticNoBoundOperator<double> >(qi::_1)];
probabilisticNoBoundOperator.name("no bound operator");
steadyStateNoBoundOperator = (qi::lit("S") >> qi::lit("=") >> qi::lit("?") >> qi::lit("[") >> stateFormula >> qi::lit("]"))[qi::_val =
phoenix::new_<storm::property::csl::SteadyStateNoBoundOperator<double> >(qi::_1)];
steadyStateNoBoundOperator.name("no bound operator");
steadyStateBoundOperator.name("steady state bound operator");
//This block defines rules for parsing probabilistic path formulas
pathFormula = (timeBoundedEventually | eventually | globally | next | timeBoundedUntil | until);
pathFormula = (timeBoundedEventually | eventually | globally | next | timeBoundedUntil | until | (qi::lit("(") >> pathFormula >> qi::lit(")")) | (qi::lit("[") >> pathFormula >> qi::lit("]")));
pathFormula.name("path formula");
timeBoundedEventually = (
(qi::lit("F") >> qi::lit("[") > qi::double_ > qi::lit(",") > qi::double_ > qi::lit("]") > stateFormula)[qi::_val =
phoenix::new_<storm::property::csl::TimeBoundedEventually<double>>(qi::_1, qi::_2, qi::_3)] |
(qi::lit("F") >> qi::lit("[") >> qi::double_ >> qi::lit(",") > qi::double_ > qi::lit("]") > stateFormula)[qi::_val =
MAKE(csl::TimeBoundedEventually<double>, qi::_1, qi::_2, qi::_3)] |
(qi::lit("F") >> (qi::lit("<=") | qi::lit("<")) > qi::double_ > stateFormula)[qi::_val =
phoenix::new_<storm::property::csl::TimeBoundedEventually<double>>(0, qi::_1, qi::_2)] |
MAKE(csl::TimeBoundedEventually<double>, 0, qi::_1, qi::_2)] |
(qi::lit("F") >> (qi::lit(">=") | qi::lit(">")) > qi::double_ > stateFormula)[qi::_val =
phoenix::new_<storm::property::csl::TimeBoundedEventually<double>>(qi::_1, std::numeric_limits<double>::infinity(), qi::_2)]
MAKE(csl::TimeBoundedEventually<double>, qi::_1, std::numeric_limits<double>::infinity(), qi::_2)]
);
timeBoundedEventually.name("path formula (for probabilistic operator)");
timeBoundedEventually.name("time bounded eventually");
eventually = (qi::lit("F") > stateFormula)[qi::_val =
phoenix::new_<storm::property::csl::Eventually<double> >(qi::_1)];
eventually.name("path formula (for probabilistic operator)");
MAKE(csl::Eventually<double> , qi::_1)];
eventually.name("eventually");
next = (qi::lit("X") > stateFormula)[qi::_val =
phoenix::new_<storm::property::csl::Next<double> >(qi::_1)];
next.name("path formula (for probabilistic operator)");
MAKE(csl::Next<double> , qi::_1)];
next.name("next");
globally = (qi::lit("G") > stateFormula)[qi::_val =
phoenix::new_<storm::property::csl::Globally<double> >(qi::_1)];
globally.name("path formula (for probabilistic operator)");
MAKE(csl::Globally<double> , qi::_1)];
globally.name("globally");
timeBoundedUntil = (
(stateFormula[qi::_a = phoenix::construct<std::shared_ptr<storm::property::csl::AbstractStateFormula<double>>>(qi::_1)] >> qi::lit("U") >> qi::lit("[") > qi::double_ > qi::lit(",") > qi::double_ > qi::lit("]") > stateFormula)
[qi::_val = phoenix::new_<storm::property::csl::TimeBoundedUntil<double>>(qi::_2, qi::_3, phoenix::bind(&storm::property::csl::AbstractStateFormula<double>::clone, phoenix::bind(&std::shared_ptr<storm::property::csl::AbstractStateFormula<double>>::get, qi::_a)), qi::_4)] |
(stateFormula[qi::_a = phoenix::construct<std::shared_ptr<storm::property::csl::AbstractStateFormula<double>>>(qi::_1)] >> qi::lit("U") >> (qi::lit("<=") | qi::lit("<")) > qi::double_ > stateFormula)
[qi::_val = phoenix::new_<storm::property::csl::TimeBoundedUntil<double>>(0, qi::_2, phoenix::bind(&storm::property::csl::AbstractStateFormula<double>::clone, phoenix::bind(&std::shared_ptr<storm::property::csl::AbstractStateFormula<double>>::get, qi::_a)), qi::_3)] |
(stateFormula[qi::_a = phoenix::construct<std::shared_ptr<storm::property::csl::AbstractStateFormula<double>>>(qi::_1)] >> qi::lit("U") >> (qi::lit(">=") | qi::lit(">")) > qi::double_ > stateFormula)
[qi::_val = phoenix::new_<storm::property::csl::TimeBoundedUntil<double>>(qi::_2, std::numeric_limits<double>::infinity(), phoenix::bind(&storm::property::csl::AbstractStateFormula<double>::clone, phoenix::bind(&std::shared_ptr<storm::property::csl::AbstractStateFormula<double>>::get, qi::_a)), qi::_3)]
(stateFormula[qi::_a = qi::_1] >> qi::lit("U") >> qi::lit("[") >> qi::double_ >> qi::lit(",") >> qi::double_ >> qi::lit("]") >> stateFormula)
[qi::_val = MAKE(csl::TimeBoundedUntil<double>, qi::_2, qi::_3, qi::_a, qi::_4)] |
(stateFormula[qi::_a = qi::_1] >> qi::lit("U") >> (qi::lit("<=") | qi::lit("<")) > qi::double_ > stateFormula)
[qi::_val = MAKE(csl::TimeBoundedUntil<double>, 0, qi::_2, qi::_a, qi::_3)] |
(stateFormula[qi::_a = qi::_1] >> qi::lit("U") >> (qi::lit(">=") | qi::lit(">")) > qi::double_ > stateFormula)
[qi::_val = MAKE(csl::TimeBoundedUntil<double>, qi::_2, std::numeric_limits<double>::infinity(), qi::_a, qi::_3)]
);
timeBoundedUntil.name("path formula (for probabilistic operator)");
until = (stateFormula[qi::_a = phoenix::construct<std::shared_ptr<storm::property::csl::AbstractStateFormula<double>>>(qi::_1)] >> qi::lit("U") > stateFormula)[qi::_val =
phoenix::new_<storm::property::csl::Until<double>>(phoenix::bind(&storm::property::csl::AbstractStateFormula<double>::clone, phoenix::bind(&std::shared_ptr<storm::property::csl::AbstractStateFormula<double>>::get, qi::_a)), qi::_2)];
until.name("path formula (for probabilistic operator)");
timeBoundedUntil.name("time bounded until");
until = (stateFormula[qi::_a = qi::_1] >> qi::lit("U") > stateFormula)[qi::_val =
MAKE(csl::Until<double>, qi::_a, qi::_2)];
until.name("until formula");
formula = (noBoundOperator | stateFormula);
formula = (pathFormula | stateFormula);
formula.name("CSL formula");
start = (((formula) > (comment | qi::eps))[qi::_val = qi::_1] |
comment
) > qi::eoi;
start.name("CSL formula");
//This block defines rules for parsing formulas with noBoundOperators
noBoundOperator = (probabilisticNoBoundOperator | steadyStateNoBoundOperator);
noBoundOperator.name("no bound operator");
probabilisticNoBoundOperator =
(qi::lit("P") >> qi::lit("min") >> qi::lit("=") > qi::lit("?") >> pathFormula)[qi::_val =
MAKE(csl::CslFilter<double>, qi::_1, storm::properties::MINIMIZE)] |
(qi::lit("P") >> qi::lit("max") >> qi::lit("=") > qi::lit("?") >> pathFormula)[qi::_val =
MAKE(csl::CslFilter<double>, qi::_1, storm::properties::MAXIMIZE)] |
(qi::lit("P") >> qi::lit("=") > qi::lit("?") >> pathFormula)[qi::_val =
MAKE(csl::CslFilter<double>, qi::_1)];
probabilisticNoBoundOperator.name("probabilistic no bound operator");
steadyStateNoBoundOperator = (qi::lit("S") >> qi::lit("=") > qi::lit("?") >> stateFormula )[qi::_val =
MAKE(csl::CslFilter<double>, qi::_1, storm::properties::UNDEFINED, true)];
steadyStateNoBoundOperator.name("steady state no bound operator");
// This block defines rules for parsing filter actions.
boundAction = (qi::lit("bound") > qi::lit("(") >> comparisonType >> qi::lit(",") >> qi::double_ >> qi::lit(")"))[qi::_val =
MAKE(storm::properties::action::BoundAction<double> ,qi::_1, qi::_2)];
boundAction.name("bound action");
invertAction = qi::lit("invert")[qi::_val = MAKE(storm::properties::action::InvertAction<double>, )];
invertAction.name("invert action");
formulaAction = (qi::lit("formula") > qi::lit("(") >> stateFormula >> qi::lit(")"))[qi::_val =
MAKE(storm::properties::action::FormulaAction<double>, qi::_1)];
formulaAction.name("formula action");
rangeAction = (
(qi::lit("range") >> qi::lit("(") >> qi::uint_ >> qi::lit(",") > qi::uint_ >> qi::lit(")"))[qi::_val =
MAKE(storm::properties::action::RangeAction<double>, qi::_1, qi::_2)] |
(qi::lit("range") >> qi::lit("(") >> qi::uint_ >> qi::lit(")"))[qi::_val =
MAKE(storm::properties::action::RangeAction<double>, qi::_1, qi::_1 + 1)]
);
rangeAction.name("range action");
sortAction = (
(qi::lit("sort") >> qi::lit("(") >> sortingCategory >> qi::lit(")"))[qi::_val =
MAKE(storm::properties::action::SortAction<double>, qi::_1)] |
(qi::lit("sort") >> qi::lit("(") >> sortingCategory >> qi::lit(", ") >> (qi::lit("ascending") | qi::lit("asc")) > qi::lit(")"))[qi::_val =
MAKE(storm::properties::action::SortAction<double>, qi::_1, true)] |
(qi::lit("sort") >> qi::lit("(") >> sortingCategory >> qi::lit(", ") >> (qi::lit("descending") | qi::lit("desc")) > qi::lit(")"))[qi::_val =
MAKE(storm::properties::action::SortAction<double>, qi::_1, false)]
);
sortAction.name("sort action");
abstractAction = (qi::lit(";") | qi::eps) >> (boundAction | invertAction | formulaAction | rangeAction | sortAction) >> (qi::lit(";") | qi::eps);
abstractAction.name("filter action");
filter = (qi::lit("filter") >> qi::lit("[") >> +abstractAction >> qi::lit("]") >> qi::lit("(") >> formula >> qi::lit(")"))[qi::_val =
MAKE(csl::CslFilter<double>, qi::_2, qi::_1)] |
(qi::lit("filter") >> qi::lit("[") >> qi::lit("max") > +abstractAction >> qi::lit("]") >> qi::lit("(") >> formula >> qi::lit(")"))[qi::_val =
MAKE(csl::CslFilter<double>, qi::_2, qi::_1, storm::properties::MAXIMIZE)] |
(qi::lit("filter") >> qi::lit("[") >> qi::lit("min") > +abstractAction >> qi::lit("]") >> qi::lit("(") >> formula >> qi::lit(")"))[qi::_val =
MAKE(csl::CslFilter<double>, qi::_2, qi::_1, storm::properties::MINIMIZE)] |
(noBoundOperator)[qi::_val =
qi::_1] |
(formula)[qi::_val =
MAKE(csl::CslFilter<double>, qi::_1)];
filter.name("CSL formula filter");
start = (((filter) > (comment | qi::eps))[qi::_val = qi::_1] | comment[qi::_val = MAKE(csl::CslFilter<double>, nullptr)] ) > qi::eoi;
start.name("CSL formula filter start");
}
qi::rule<Iterator, storm::property::csl::AbstractCslFormula<double>*(), Skipper> start;
qi::rule<Iterator, storm::property::csl::AbstractCslFormula<double>*(), Skipper> formula;
qi::rule<Iterator, storm::property::csl::AbstractCslFormula<double>*(), Skipper> comment;
qi::rule<Iterator, std::shared_ptr<csl::CslFilter<double>>(), Skipper> start;
qi::rule<Iterator, std::shared_ptr<csl::CslFilter<double>>(), Skipper> filter;
qi::rule<Iterator, std::shared_ptr<csl::CslFilter<double>>(), Skipper> noBoundOperator;
qi::rule<Iterator, std::shared_ptr<csl::CslFilter<double>>(), Skipper> probabilisticNoBoundOperator;
qi::rule<Iterator, std::shared_ptr<csl::CslFilter<double>>(), Skipper> steadyStateNoBoundOperator;
qi::rule<Iterator, std::shared_ptr<storm::properties::action::AbstractAction<double>>(), Skipper> abstractAction;
qi::rule<Iterator, std::shared_ptr<storm::properties::action::BoundAction<double>>(), Skipper> boundAction;
qi::rule<Iterator, std::shared_ptr<storm::properties::action::InvertAction<double>>(), Skipper> invertAction;
qi::rule<Iterator, std::shared_ptr<storm::properties::action::FormulaAction<double>>(), Skipper> formulaAction;
qi::rule<Iterator, std::shared_ptr<storm::properties::action::RangeAction<double>>(), Skipper> rangeAction;
qi::rule<Iterator, std::shared_ptr<storm::properties::action::SortAction<double>>(), Skipper> sortAction;
qi::rule<Iterator, storm::property::csl::AbstractStateFormula<double>*(), Skipper> stateFormula;
qi::rule<Iterator, storm::property::csl::AbstractStateFormula<double>*(), Skipper> atomicStateFormula;
qi::rule<Iterator, std::shared_ptr<csl::AbstractCslFormula<double>>(), Skipper> formula;
qi::rule<Iterator, std::shared_ptr<csl::AbstractCslFormula<double>>(), Skipper> comment;
qi::rule<Iterator, storm::property::csl::AbstractStateFormula<double>*(), Skipper> andFormula;
qi::rule<Iterator, storm::property::csl::AbstractStateFormula<double>*(), Skipper> atomicProposition;
qi::rule<Iterator, storm::property::csl::AbstractStateFormula<double>*(), Skipper> orFormula;
qi::rule<Iterator, storm::property::csl::AbstractStateFormula<double>*(), Skipper> notFormula;
qi::rule<Iterator, storm::property::csl::ProbabilisticBoundOperator<double>*(), Skipper> probabilisticBoundOperator;
qi::rule<Iterator, storm::property::csl::SteadyStateBoundOperator<double>*(), Skipper> steadyStateBoundOperator;
qi::rule<Iterator, std::shared_ptr<csl::AbstractStateFormula<double>>(), Skipper> stateFormula;
qi::rule<Iterator, std::shared_ptr<csl::AbstractStateFormula<double>>(), Skipper> atomicStateFormula;
qi::rule<Iterator, storm::property::csl::AbstractNoBoundOperator<double>*(), Skipper> noBoundOperator;
qi::rule<Iterator, storm::property::csl::AbstractNoBoundOperator<double>*(), Skipper> probabilisticNoBoundOperator;
qi::rule<Iterator, storm::property::csl::AbstractNoBoundOperator<double>*(), Skipper> steadyStateNoBoundOperator;
qi::rule<Iterator, std::shared_ptr<csl::AbstractStateFormula<double>>(), Skipper> andFormula;
qi::rule<Iterator, std::shared_ptr<csl::AbstractStateFormula<double>>(), Skipper> atomicProposition;
qi::rule<Iterator, std::shared_ptr<csl::AbstractStateFormula<double>>(), Skipper> orFormula;
qi::rule<Iterator, std::shared_ptr<csl::AbstractStateFormula<double>>(), Skipper> notFormula;
qi::rule<Iterator, std::shared_ptr<csl::ProbabilisticBoundOperator<double>>(), Skipper> probabilisticBoundOperator;
qi::rule<Iterator, std::shared_ptr<csl::SteadyStateBoundOperator<double>>(), Skipper> steadyStateBoundOperator;
qi::rule<Iterator, storm::property::csl::AbstractPathFormula<double>*(), Skipper> pathFormula;
qi::rule<Iterator, storm::property::csl::TimeBoundedEventually<double>*(), Skipper> timeBoundedEventually;
qi::rule<Iterator, storm::property::csl::Eventually<double>*(), Skipper> eventually;
qi::rule<Iterator, storm::property::csl::Next<double>*(), Skipper> next;
qi::rule<Iterator, storm::property::csl::Globally<double>*(), Skipper> globally;
qi::rule<Iterator, storm::property::csl::TimeBoundedUntil<double>*(), qi::locals< std::shared_ptr<storm::property::csl::AbstractStateFormula<double>>>, Skipper> timeBoundedUntil;
qi::rule<Iterator, storm::property::csl::Until<double>*(), qi::locals< std::shared_ptr<storm::property::csl::AbstractStateFormula<double>>>, Skipper> until;
qi::rule<Iterator, std::shared_ptr<csl::AbstractPathFormula<double>>(), Skipper> pathFormula;
qi::rule<Iterator, std::shared_ptr<csl::TimeBoundedEventually<double>>(), Skipper> timeBoundedEventually;
qi::rule<Iterator, std::shared_ptr<csl::Eventually<double>>(), Skipper> eventually;
qi::rule<Iterator, std::shared_ptr<csl::Next<double>>(), Skipper> next;
qi::rule<Iterator, std::shared_ptr<csl::Globally<double>>(), Skipper> globally;
qi::rule<Iterator, std::shared_ptr<csl::TimeBoundedUntil<double>>(), qi::locals< std::shared_ptr<storm::properties::csl::AbstractStateFormula<double>>>, Skipper> timeBoundedUntil;
qi::rule<Iterator, std::shared_ptr<csl::Until<double>>(), qi::locals< std::shared_ptr<storm::properties::csl::AbstractStateFormula<double>>>, Skipper> until;
qi::rule<Iterator, std::string(), Skipper> freeIdentifierName;
qi::rule<Iterator, storm::property::ComparisonType(), Skipper> comparisonType;
qi::rule<Iterator, storm::properties::ComparisonType(), Skipper> comparisonType;
qi::rule<Iterator, storm::properties::action::SortAction<double>::SortingCategory(), Skipper> sortingCategory;
};
storm::property::csl::AbstractCslFormula<double>* CslParser(std::string formulaString) {
std::shared_ptr<storm::properties::csl::CslFilter<double>> CslParser::parseCslFormula(std::string formulaString) {
// Prepare iterators to input.
BaseIteratorType stringIteratorBegin = formulaString.begin();
BaseIteratorType stringIteratorEnd = formulaString.end();
@ -175,7 +248,7 @@ storm::property::csl::AbstractCslFormula<double>* CslParser(std::string formulaS
// Prepare resulting intermediate representation of input.
storm::property::csl::AbstractCslFormula<double>* result_pointer = nullptr;
std::shared_ptr<storm::properties::csl::CslFilter<double>> result_pointer(nullptr);
CslGrammar<PositionIteratorType, BOOST_TYPEOF(boost::spirit::ascii::space)> grammar;
@ -212,7 +285,7 @@ storm::property::csl::AbstractCslFormula<double>* CslParser(std::string formulaS
// The syntax can be so wrong that no rule can be matched at all
// In that case, no expectation failure is thrown, but the parser just returns nullptr
// Then, of course the result is not usable, hence we throw a WrongFormatException, too.
if (result_pointer == nullptr) {
if (!result_pointer) {
throw storm::exceptions::WrongFormatException() << "Syntax error in formula";
}

40
src/parser/CslParser.h

@ -8,28 +8,42 @@
#ifndef STORM_PARSER_CSLPARSER_H_
#define STORM_PARSER_CSLPARSER_H_
#include "src/formula/Csl.h"
#include "src/properties/Csl.h"
#include "src/properties/csl/CslFilter.h"
#include <functional>
namespace storm {
namespace parser {
/*!
* Reads a CSL formula from its string representation and parses it into a formula tree, consisting of
* classes in the namespace storm::property.
* Reads a Csl formula from a string and returns the formula tree.
*
* If the string could not be parsed successfully, it will throw a wrongFormatException.
*
* @param formulaString The string representation of the formula
* @throw wrongFormatException If the input could not be parsed successfully
* If you want to read the formula from a file, use the LtlFileParser class instead.
*/
storm::property::csl::AbstractCslFormula<double>* CslParser(std::string formulaString);
class CslParser {
public:
/*!
* Struct for the CSL grammar, that Boost::Spirit uses to parse the formulas.
*/
template<typename Iterator, typename Skipper>
struct CslGrammar;
/*!
* Reads a CSL formula from its string representation and parses it into a formula tree, consisting of
* classes in the namespace storm::properties.
*
* If the string could not be parsed successfully, it will throw a wrongFormatException.
*
* @param formulaString The string representation of the formula.
* @throw wrongFormatException If the input could not be parsed successfully.
* @return A CslFilter maintaining the parsed formula.
*/
static std::shared_ptr<storm::properties::csl::CslFilter<double>> parseCslFormula(std::string formulaString);
private:
/*!
* Struct for the CSL grammar, that Boost::Spirit uses to parse the formulas.
*/
template<typename Iterator, typename Skipper>
struct CslGrammar;
};
} /* namespace parser */
} /* namespace storm */

6
src/parser/LtlFileParser.cpp

@ -15,7 +15,7 @@
namespace storm {
namespace parser {
std::list<storm::property::ltl::AbstractLtlFormula<double>*> LtlFileParser(std::string filename) {
std::list<std::shared_ptr<storm::properties::ltl::LtlFilter<double>>> LtlFileParser::parseLtlFile(std::string filename) {
// Open file
std::ifstream inputFileStream(filename, std::ios::in);
@ -24,13 +24,13 @@ std::list<storm::property::ltl::AbstractLtlFormula<double>*> LtlFileParser(std::
throw storm::exceptions::FileIoException() << message << filename;
}
std::list<storm::property::ltl::AbstractLtlFormula<double>*> result;
std::list<std::shared_ptr<storm::properties::ltl::LtlFilter<double>>> result;
while(!inputFileStream.eof()) {
std::string line;
//The while loop reads the input file line by line
while (std::getline(inputFileStream, line)) {
result.push_back(storm::parser::LtlParser(line));
result.push_back(storm::parser::LtlParser::parseLtlFormula(line));
}
}

21
src/parser/LtlFileParser.h

@ -8,20 +8,25 @@
#ifndef LTLFILEPARSER_H_
#define LTLFILEPARSER_H_
#include "formula/Ltl.h"
#include "properties/Ltl.h"
#include "src/properties/ltl/LtlFilter.h"
#include <list>
namespace storm {
namespace parser {
/*!
* Parses each line of a given file as prctl formula and returns a list containing the results of the parsing.
*
* @param filename
* @return The list of parsed formulas
*/
std::list<storm::property::ltl::AbstractLtlFormula<double>*> LtlFileParser(std::string filename);
class LtlFileParser {
public:
/*!
* Parses each line of a given file as prctl formula and returns a list containing the results of the parsing.
*
* @param filename Name and path to the file in which the formula strings can be found.
* @return The list of parsed formulas.
*/
static std::list<std::shared_ptr<storm::properties::ltl::LtlFilter<double>>> parseLtlFile(std::string filename);
};
} //namespace parser
} //namespace storm

191
src/parser/LtlParser.cpp

@ -10,6 +10,13 @@
#include "src/utility/OsDetection.h"
#include "src/utility/constants.h"
// The action class headers.
#include "src/properties/actions/AbstractAction.h"
#include "src/properties/actions/BoundAction.h"
#include "src/properties/actions/InvertAction.h"
#include "src/properties/actions/RangeAction.h"
#include "src/properties/actions/SortAction.h"
// If the parser fails due to ill-formed data, this exception is thrown.
#include "src/exceptions/WrongFormatException.h"
@ -29,11 +36,12 @@
// Some typedefs and namespace definitions to reduce code size.
#define MAKE(Type, ...) phoenix::construct<std::shared_ptr<Type>>(phoenix::new_<Type>(__VA_ARGS__))
typedef std::string::const_iterator BaseIteratorType;
typedef boost::spirit::classic::position_iterator2<BaseIteratorType> PositionIteratorType;
namespace qi = boost::spirit::qi;
namespace phoenix = boost::phoenix;
namespace ltl = storm::properties::ltl;
namespace storm {
@ -41,94 +49,141 @@ namespace storm {
namespace parser {
template<typename Iterator, typename Skipper>
struct LtlGrammar : qi::grammar<Iterator, storm::property::ltl::AbstractLtlFormula<double>*(), Skipper > {
struct LtlParser::LtlGrammar : qi::grammar<Iterator, std::shared_ptr<storm::properties::ltl::LtlFilter<double>>(), Skipper > {
LtlGrammar() : LtlGrammar::base_type(start) {
//This block contains helper rules that may be used several times
freeIdentifierName = qi::lexeme[qi::alpha >> *(qi::alnum | qi::char_('_'))];
//Comment: Empty line or line starting with "//"
comparisonType = (
(qi::lit(">="))[qi::_val = storm::properties::GREATER_EQUAL] |
(qi::lit(">"))[qi::_val = storm::properties::GREATER] |
(qi::lit("<="))[qi::_val = storm::properties::LESS_EQUAL] |
(qi::lit("<"))[qi::_val = storm::properties::LESS]);
sortingCategory = (
(qi::lit("index"))[qi::_val = storm::properties::action::SortAction<double>::INDEX] |
(qi::lit("value"))[qi::_val = storm::properties::action::SortAction<double>::VALUE]
);
// Comment: Empty line or line starting with "//"
comment = (qi::lit("//") >> *(qi::char_))[qi::_val = nullptr];
freeIdentifierName = qi::lexeme[+(qi::alpha | qi::char_('_'))];
//This block defines rules for parsing state formulas
ltlFormula %= orFormula;
ltlFormula.name("LTL formula");
// This block defines rules for parsing state formulas
formula %= orFormula;
formula.name("LTL formula");
orFormula = andFormula[qi::_val = qi::_1] > *(qi::lit("|") > andFormula)[qi::_val =
phoenix::new_<storm::property::ltl::Or<double>>(qi::_val, qi::_1)];
orFormula.name("LTL formula");
MAKE(ltl::Or<double>, qi::_val, qi::_1)];
orFormula.name("Or");
andFormula = untilFormula[qi::_val = qi::_1] > *(qi::lit("&") > untilFormula)[qi::_val =
phoenix::new_<storm::property::ltl::And<double>>(qi::_val, qi::_1)];
andFormula.name("LTL formula");
MAKE(ltl::And<double>, qi::_val, qi::_1)];
andFormula.name("And");
untilFormula = notFormula[qi::_val = qi::_1] >
*((qi::lit("U") >> qi::lit("<=") > qi::int_ > notFormula)[qi::_val = phoenix::new_<storm::property::ltl::BoundedUntil<double>>(qi::_val, qi::_2, qi::_1)] |
(qi::lit("U") > notFormula)[qi::_val = phoenix::new_<storm::property::ltl::Until<double>>(qi::_val, qi::_1)]);
*((qi::lit("U") >> qi::lit("<=") > qi::int_ > notFormula)[qi::_val = MAKE(ltl::BoundedUntil<double>, qi::_val, qi::_2, qi::_1)] |
(qi::lit("U") > notFormula)[qi::_val = MAKE(ltl::Until<double>, qi::_val, qi::_1)]);
until.name("Until");
notFormula = atomicLtlFormula[qi::_val = qi::_1] | (qi::lit("!") > atomicLtlFormula)[qi::_val =
phoenix::new_<storm::property::ltl::Not<double>>(qi::_1)];
notFormula.name("LTL formula");
MAKE(ltl::Not<double>, qi::_1)];
notFormula.name("Not");
//This block defines rules for "atomic" state formulas
//(Propositions, probabilistic/reward formulas, and state formulas in brackets)
atomicLtlFormula %= pathFormula | atomicProposition | qi::lit("(") >> ltlFormula >> qi::lit(")");
atomicLtlFormula.name("LTL formula");
atomicLtlFormula %= pathFormula | atomicProposition | qi::lit("(") >> formula >> qi::lit(")")| qi::lit("[") >> formula >> qi::lit("]");
atomicLtlFormula.name("Atomic LTL formula");
atomicProposition = (freeIdentifierName)[qi::_val =
phoenix::new_<storm::property::ltl::Ap<double>>(qi::_1)];
atomicProposition.name("LTL formula");
MAKE(ltl::Ap<double>, qi::_1)];
atomicProposition.name("Atomic Proposition");
//This block defines rules for parsing probabilistic path formulas
pathFormula = (boundedEventually | eventually | globally | next);
pathFormula.name("LTL formula");
boundedEventually = (qi::lit("F") >> qi::lit("<=") > qi::int_ > ltlFormula)[qi::_val =
phoenix::new_<storm::property::ltl::BoundedEventually<double>>(qi::_2, qi::_1)];
boundedEventually.name("LTL formula");
eventually = (qi::lit("F") >> ltlFormula)[qi::_val =
phoenix::new_<storm::property::ltl::Eventually<double> >(qi::_1)];
eventually.name("LTL formula");
globally = (qi::lit("G") >> ltlFormula)[qi::_val =
phoenix::new_<storm::property::ltl::Globally<double> >(qi::_1)];
globally.name("LTL formula");
next = (qi::lit("X") >> ltlFormula)[qi::_val =
phoenix::new_<storm::property::ltl::Next<double> >(qi::_1)];
next.name("LTL formula");
start = (((ltlFormula) > (comment | qi::eps))[qi::_val = qi::_1] |
comment
) > qi::eoi;
start.name("LTL formula");
pathFormula.name("Path Formula");
boundedEventually = (qi::lit("F") >> qi::lit("<=") > qi::int_ > formula)[qi::_val =
MAKE(ltl::BoundedEventually<double>, qi::_2, qi::_1)];
boundedEventually.name("Bounded Eventually");
eventually = (qi::lit("F") >> formula)[qi::_val =
MAKE(ltl::Eventually<double>, qi::_1)];
eventually.name("Eventually");
globally = (qi::lit("G") >> formula)[qi::_val =
MAKE(ltl::Globally<double>, qi::_1)];
globally.name("Globally");
next = (qi::lit("X") >> formula)[qi::_val =
MAKE(ltl::Next<double>, qi::_1)];
next.name("Next");
// This block defines rules for parsing filter actions.
boundAction = (qi::lit("bound") > qi::lit("(") >> comparisonType >> qi::lit(",") >> qi::double_ >> qi::lit(")"))[qi::_val =
MAKE(storm::properties::action::BoundAction<double> ,qi::_1, qi::_2)];
boundAction.name("bound action");
invertAction = qi::lit("invert")[qi::_val = MAKE(storm::properties::action::InvertAction<double>, )];
invertAction.name("invert action");
rangeAction = (
(qi::lit("range") >> qi::lit("(") >> qi::uint_ >> qi::lit(",") > qi::uint_ >> qi::lit(")"))[qi::_val =
MAKE(storm::properties::action::RangeAction<double>, qi::_1, qi::_2)] |
(qi::lit("range") >> qi::lit("(") >> qi::uint_ >> qi::lit(")"))[qi::_val =
MAKE(storm::properties::action::RangeAction<double>, qi::_1, qi::_1 + 1)]
);
rangeAction.name("range action");
sortAction = (
(qi::lit("sort") >> qi::lit("(") >> sortingCategory >> qi::lit(")"))[qi::_val =
MAKE(storm::properties::action::SortAction<double>, qi::_1)] |
(qi::lit("sort") >> qi::lit("(") >> sortingCategory >> qi::lit(", ") >> (qi::lit("ascending") | qi::lit("asc")) > qi::lit(")"))[qi::_val =
MAKE(storm::properties::action::SortAction<double>, qi::_1, true)] |
(qi::lit("sort") >> qi::lit("(") >> sortingCategory >> qi::lit(", ") >> (qi::lit("descending") | qi::lit("desc")) > qi::lit(")"))[qi::_val =
MAKE(storm::properties::action::SortAction<double>, qi::_1, false)]
);
sortAction.name("sort action");
abstractAction = (qi::lit(";") | qi::eps) >> (boundAction | invertAction | rangeAction | sortAction) >> (qi::lit(";") | qi::eps);
abstractAction.name("filter action");
filter = (qi::lit("filter") >> qi::lit("[") >> +abstractAction >> qi::lit("]") > qi::lit("(") >> formula >> qi::lit(")"))[qi::_val =
MAKE(ltl::LtlFilter<double>, qi::_2, qi::_1)] |
(qi::lit("filter") >> qi::lit("[") >> qi::lit("max") > +abstractAction >> qi::lit("]") >> qi::lit("(") >> formula >> qi::lit(")"))[qi::_val =
MAKE(ltl::LtlFilter<double>, qi::_2, qi::_1, storm::properties::MAXIMIZE)] |
(qi::lit("filter") >> qi::lit("[") >> qi::lit("min") > +abstractAction >> qi::lit("]") >> qi::lit("(") >> formula >> qi::lit(")"))[qi::_val =
MAKE(ltl::LtlFilter<double>, qi::_2, qi::_1, storm::properties::MINIMIZE)] |
(formula)[qi::_val =
MAKE(ltl::LtlFilter<double>, qi::_1)];
filter.name("LTL formula filter");
start = (((filter) > (comment | qi::eps))[qi::_val = qi::_1] | comment[qi::_val = MAKE(ltl::LtlFilter<double>, nullptr)] ) > qi::eoi;
start.name("start");
}
qi::rule<Iterator, storm::property::ltl::AbstractLtlFormula<double>*(), Skipper> start;
qi::rule<Iterator, storm::property::ltl::AbstractLtlFormula<double>*(), Skipper> comment;
qi::rule<Iterator, storm::property::ltl::AbstractLtlFormula<double>*(), Skipper> ltlFormula;
qi::rule<Iterator, storm::property::ltl::AbstractLtlFormula<double>*(), Skipper> atomicLtlFormula;
qi::rule<Iterator, storm::property::ltl::AbstractLtlFormula<double>*(), Skipper> andFormula;
qi::rule<Iterator, storm::property::ltl::AbstractLtlFormula<double>*(), Skipper> untilFormula;
qi::rule<Iterator, storm::property::ltl::AbstractLtlFormula<double>*(), Skipper> atomicProposition;
qi::rule<Iterator, storm::property::ltl::AbstractLtlFormula<double>*(), Skipper> orFormula;
qi::rule<Iterator, storm::property::ltl::AbstractLtlFormula<double>*(), Skipper> notFormula;
//qi::rule<Iterator, storm::property::ltl::ProbabilisticBoundOperator<double>*(), Skipper> probabilisticBoundOperator;
//qi::rule<Iterator, storm::property::ltl::AbstractNoBoundOperator<double>*(), Skipper> noBoundOperator;
//qi::rule<Iterator, storm::property::ltl::AbstractNoBoundOperator<double>*(), Skipper> probabilisticNoBoundOperator;
qi::rule<Iterator, storm::property::ltl::AbstractLtlFormula<double>*(), Skipper> pathFormula;
qi::rule<Iterator, storm::property::ltl::BoundedEventually<double>*(), Skipper> boundedEventually;
qi::rule<Iterator, storm::property::ltl::Eventually<double>*(), Skipper> eventually;
qi::rule<Iterator, storm::property::ltl::Globally<double>*(), Skipper> globally;
qi::rule<Iterator, storm::property::ltl::Next<double>*(), Skipper> next;
qi::rule<Iterator, storm::property::ltl::AbstractLtlFormula<double>*(), qi::locals< std::shared_ptr<storm::property::ltl::AbstractLtlFormula<double>>>, Skipper> boundedUntil;
qi::rule<Iterator, storm::property::ltl::AbstractLtlFormula<double>*(), qi::locals< std::shared_ptr<storm::property::ltl::AbstractLtlFormula<double>>>, Skipper> until;
qi::rule<Iterator, std::shared_ptr<storm::properties::ltl::LtlFilter<double>>(), Skipper> start;
qi::rule<Iterator, std::shared_ptr<storm::properties::ltl::LtlFilter<double>>(), Skipper> filter;
qi::rule<Iterator, std::shared_ptr<storm::properties::action::AbstractAction<double>>(), Skipper> abstractAction;
qi::rule<Iterator, std::shared_ptr<storm::properties::action::BoundAction<double>>(), Skipper> boundAction;
qi::rule<Iterator, std::shared_ptr<storm::properties::action::InvertAction<double>>(), Skipper> invertAction;
qi::rule<Iterator, std::shared_ptr<storm::properties::action::RangeAction<double>>(), Skipper> rangeAction;
qi::rule<Iterator, std::shared_ptr<storm::properties::action::SortAction<double>>(), Skipper> sortAction;
qi::rule<Iterator, std::shared_ptr<storm::properties::ltl::AbstractLtlFormula<double>>(), Skipper> comment;
qi::rule<Iterator, std::shared_ptr<storm::properties::ltl::AbstractLtlFormula<double>>(), Skipper> formula;
qi::rule<Iterator, std::shared_ptr<storm::properties::ltl::AbstractLtlFormula<double>>(), Skipper> atomicLtlFormula;
qi::rule<Iterator, std::shared_ptr<storm::properties::ltl::AbstractLtlFormula<double>>(), Skipper> andFormula;
qi::rule<Iterator, std::shared_ptr<storm::properties::ltl::AbstractLtlFormula<double>>(), Skipper> untilFormula;
qi::rule<Iterator, std::shared_ptr<storm::properties::ltl::AbstractLtlFormula<double>>(), Skipper> atomicProposition;
qi::rule<Iterator, std::shared_ptr<storm::properties::ltl::AbstractLtlFormula<double>>(), Skipper> orFormula;
qi::rule<Iterator, std::shared_ptr<storm::properties::ltl::AbstractLtlFormula<double>>(), Skipper> notFormula;
qi::rule<Iterator, std::shared_ptr<storm::properties::ltl::AbstractLtlFormula<double>>(), Skipper> pathFormula;
qi::rule<Iterator, std::shared_ptr<storm::properties::ltl::BoundedEventually<double>>(), Skipper> boundedEventually;
qi::rule<Iterator, std::shared_ptr<storm::properties::ltl::Eventually<double>>(), Skipper> eventually;
qi::rule<Iterator, std::shared_ptr<storm::properties::ltl::Globally<double>>(), Skipper> globally;
qi::rule<Iterator, std::shared_ptr<storm::properties::ltl::Next<double>>(), Skipper> next;
qi::rule<Iterator, std::shared_ptr<storm::properties::ltl::AbstractLtlFormula<double>>(), qi::locals< std::shared_ptr<storm::properties::ltl::AbstractLtlFormula<double>>>, Skipper> boundedUntil;
qi::rule<Iterator, std::shared_ptr<storm::properties::ltl::AbstractLtlFormula<double>>(), qi::locals< std::shared_ptr<storm::properties::ltl::AbstractLtlFormula<double>>>, Skipper> until;
qi::rule<Iterator, std::string(), Skipper> freeIdentifierName;
qi::rule<Iterator, storm::properties::ComparisonType(), Skipper> comparisonType;
qi::rule<Iterator, storm::properties::action::SortAction<double>::SortingCategory(), Skipper> sortingCategory;
};
} //namespace storm
} //namespace parser
storm::property::ltl::AbstractLtlFormula<double>* storm::parser::LtlParser(std::string formulaString) {
std::shared_ptr<storm::properties::ltl::LtlFilter<double>> LtlParser::parseLtlFormula(std::string formulaString) {
// Prepare iterators to input.
BaseIteratorType stringIteratorBegin = formulaString.begin();
BaseIteratorType stringIteratorEnd = formulaString.end();
@ -137,7 +192,7 @@ storm::property::ltl::AbstractLtlFormula<double>* storm::parser::LtlParser(std::
// Prepare resulting intermediate representation of input.
storm::property::ltl::AbstractLtlFormula<double>* result_pointer = nullptr;
std::shared_ptr<storm::properties::ltl::LtlFilter<double>> result_pointer(nullptr);
LtlGrammar<PositionIteratorType, BOOST_TYPEOF(boost::spirit::ascii::space)> grammar;
@ -174,10 +229,12 @@ storm::property::ltl::AbstractLtlFormula<double>* storm::parser::LtlParser(std::
// The syntax can be so wrong that no rule can be matched at all
// In that case, no expectation failure is thrown, but the parser just returns nullptr
// Then, of course the result is not usable, hence we throw a WrongFormatException, too.
if (result_pointer == nullptr) {
if (!result_pointer) {
throw storm::exceptions::WrongFormatException() << "Syntax error in formula";
}
return result_pointer;
}
} //namespace parser
} //namespace storm

34
src/parser/LtlParser.h

@ -8,27 +8,41 @@
#ifndef STORM_PARSER_LTLPARSER_H_
#define STORM_PARSER_LTLPARSER_H_
#include "src/formula/Ltl.h"
#include "src/properties/Ltl.h"
#include "src/properties/ltl/LtlFilter.h"
namespace storm {
namespace parser {
/*!
* Reads a LTL formula from a string and return the formula tree.
*
* If you want to read the formula from a file, use the LtlFileParser class instead.
*/
class LtlParser {
public:
/*!
* Reads a LTL formula from its string representation and parses it into a formula tree, consisting of
* classes in the namespace storm::property.
* classes in the namespace storm::properties.
*
* If the string could not be parsed successfully, it will throw a wrongFormatException.
*
* @param formulaString The string representation of the formula
* @throw wrongFormatException If the input could not be parsed successfully
* @param formulaString The string representation of the formula.
* @throw wrongFormatException If the input could not be parsed successfully.
* @return A LtlFilter maintaining the parsed formula.
*/
storm::property::ltl::AbstractLtlFormula<double>* LtlParser(std::string formulaString);
static std::shared_ptr<storm::properties::ltl::LtlFilter<double>> parseLtlFormula(std::string formulaString);
/*!
* Struct for the Ltl grammar, that Boost::Spirit uses to parse the formulas.
*/
template<typename Iterator, typename Skipper>
struct LtlGrammar;
private:
/*!
* Struct for the Ltl grammar, that Boost::Spirit uses to parse the formulas.
*/
template<typename Iterator, typename Skipper>
struct LtlGrammar;
};
} /* namespace parser */
} /* namespace storm */

12
src/parser/PrctlFileParser.cpp

@ -14,7 +14,7 @@
namespace storm {
namespace parser {
std::list<storm::property::prctl::AbstractPrctlFormula<double>*> PrctlFileParser(std::string filename) {
std::list<std::shared_ptr<storm::properties::prctl::PrctlFilter<double>>> PrctlFileParser::parsePrctlFile(std::string filename) {
// Open file
std::ifstream inputFileStream;
inputFileStream.open(filename, std::ios::in);
@ -24,16 +24,16 @@ std::list<storm::property::prctl::AbstractPrctlFormula<double>*> PrctlFileParser
throw storm::exceptions::FileIoException() << message << filename;
}
std::list<storm::property::prctl::AbstractPrctlFormula<double>*> result;
std::list<std::shared_ptr<storm::properties::prctl::PrctlFilter<double>>> result;
std::string line;
//The while loop reads the input file line by line
while (std::getline(inputFileStream, line)) {
PrctlParser parser(line);
if (!parser.parsedComment()) {
std::shared_ptr<storm::properties::prctl::PrctlFilter<double>> formula = PrctlParser::parsePrctlFormula(line);
if (formula != nullptr) {
//lines containing comments will be skipped.
LOG4CPLUS_INFO(logger, "Parsed formula \"" + line + "\" into \"" + parser.getFormula()->toString() + "\"");
result.push_back(parser.getFormula());
LOG4CPLUS_INFO(logger, "Parsed formula \"" + line + "\" into \"" + formula->toString() + "\"");
result.push_back(formula);
}
}

Some files were not shown because too many files changed in this diff

|||||||
100:0
Loading…
Cancel
Save