Browse Source

removed ite for ADDs as this operation should be formed with a BDD as the first argument. as a compensation, we provide a version of ite that takes a BDD and two ADDs and returns the corresponding ADD

Former-commit-id: 720dc3a9c4
main
dehnert 10 years ago
parent
commit
0708672a68
  1. 1
      resources/3rdparty/sylvan/src/sylvan_obj_bdd_storm.hpp
  2. 6
      resources/3rdparty/sylvan/src/sylvan_obj_storm.cpp
  3. 2
      src/adapters/AddExpressionAdapter.cpp
  4. 2
      src/builder/DdPrismModelBuilder.cpp
  5. 6
      src/modelchecker/prctl/helper/HybridDtmcPrctlHelper.cpp
  6. 6
      src/modelchecker/prctl/helper/HybridMdpPrctlHelper.cpp
  7. 6
      src/modelchecker/prctl/helper/SymbolicDtmcPrctlHelper.cpp
  8. 6
      src/modelchecker/prctl/helper/SymbolicMdpPrctlHelper.cpp
  9. 2
      src/modelchecker/results/HybridQuantitativeCheckResult.cpp
  10. 2
      src/modelchecker/results/SymbolicQuantitativeCheckResult.cpp
  11. 11
      src/solver/SymbolicLinearEquationSolver.cpp
  12. 4
      src/solver/SymbolicMinMaxLinearEquationSolver.cpp
  13. 9
      src/storage/dd/Add.cpp
  14. 11
      src/storage/dd/Add.h
  15. 14
      src/storage/dd/Bdd.cpp
  16. 11
      src/storage/dd/Bdd.h
  17. 7
      src/storage/dd/cudd/InternalCuddAdd.cpp
  18. 13
      src/storage/dd/cudd/InternalCuddAdd.h
  19. 8
      src/storage/dd/cudd/InternalCuddBdd.cpp
  20. 11
      src/storage/dd/cudd/InternalCuddBdd.h
  21. 7
      src/storage/dd/sylvan/InternalSylvanAdd.cpp
  22. 12
      src/storage/dd/sylvan/InternalSylvanAdd.h
  23. 9
      src/storage/dd/sylvan/InternalSylvanBdd.cpp
  24. 11
      src/storage/dd/sylvan/InternalSylvanBdd.h
  25. 8
      test/functional/storage/CuddDdTest.cpp
  26. 8
      test/functional/storage/SylvanDdTest.cpp

1
resources/3rdparty/sylvan/src/sylvan_obj_bdd_storm.hpp

@ -1,2 +1,3 @@
Mtbdd toDoubleMtbdd() const;
Mtbdd toInt64Mtbdd() const;
Mtbdd Ite(Mtbdd const& thenDd, Mtbdd const& elseDd) const;

6
resources/3rdparty/sylvan/src/sylvan_obj_storm.cpp

@ -10,6 +10,12 @@ Bdd::toInt64Mtbdd() const {
return mtbdd_bool_to_int64(bdd);
}
Mtbdd
Bdd::Ite(Mtbdd const& thenDd, Mtbdd const& elseDd) const {
LACE_ME;
return mtbdd_ite(bdd, thenDd.GetMTBDD(), elseDd.GetMTBDD());
}
Mtbdd
Mtbdd::Minus(const Mtbdd &other) const
{

2
src/adapters/AddExpressionAdapter.cpp

@ -41,7 +41,7 @@ namespace storm {
} else {
storm::dd::Add<Type, ValueType> elseDd = boost::any_cast<storm::dd::Add<Type, ValueType>>(expression.getElseExpression()->accept(*this));
storm::dd::Add<Type, ValueType> thenDd = boost::any_cast<storm::dd::Add<Type, ValueType>>(expression.getThenExpression()->accept(*this));
storm::dd::Add<Type, ValueType> conditionDd = boost::any_cast<storm::dd::Add<Type, ValueType>>(expression.getCondition()->accept(*this));
storm::dd::Bdd<Type> conditionDd = boost::any_cast<storm::dd::Bdd<Type>>(expression.getCondition()->accept(*this));
return conditionDd.ite(thenDd, elseDd);
}
}

2
src/builder/DdPrismModelBuilder.cpp

@ -683,7 +683,7 @@ namespace storm {
}
// Add a new variable that resolves the nondeterminism between the two choices.
storm::dd::Add<Type, ValueType> combinedTransitions = generationInfo.manager->getEncoding(generationInfo.nondeterminismMetaVariables[numberOfUsedNondeterminismVariables], 1).template toAdd<ValueType>().ite(action2Extended, action1Extended);
storm::dd::Add<Type, ValueType> combinedTransitions = generationInfo.manager->getEncoding(generationInfo.nondeterminismMetaVariables[numberOfUsedNondeterminismVariables], 1).ite(action2Extended, action1Extended);
return ActionDecisionDiagram((action1.guardDd.toBdd() || action2.guardDd.toBdd()).template toAdd<ValueType>(), combinedTransitions, assignedGlobalVariables, numberOfUsedNondeterminismVariables + 1);
} else {

6
src/modelchecker/prctl/helper/HybridDtmcPrctlHelper.cpp

@ -199,7 +199,7 @@ namespace storm {
if (qualitative) {
// Set the values for all maybe-states to 1 to indicate that their reward values
// are neither 0 nor infinity.
return std::unique_ptr<CheckResult>(new SymbolicQuantitativeCheckResult<DdType>(model.getReachableStates(), infinityStates.template toAdd<ValueType>().ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), model.getManager().template getAddZero<ValueType>()) + maybeStates.template toAdd<ValueType>() * model.getManager().template getAddOne<ValueType>()));
return std::unique_ptr<CheckResult>(new SymbolicQuantitativeCheckResult<DdType>(model.getReachableStates(), infinityStates.ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), model.getManager().template getAddZero<ValueType>()) + maybeStates.template toAdd<ValueType>() * model.getManager().template getAddOne<ValueType>()));
} else {
// If there are maybe states, we need to solve an equation system.
if (!maybeStates.isZero()) {
@ -233,9 +233,9 @@ namespace storm {
solver->solveEquationSystem(x, b);
// Return a hybrid check result that stores the numerical values explicitly.
return std::unique_ptr<CheckResult>(new storm::modelchecker::HybridQuantitativeCheckResult<DdType>(model.getReachableStates(), model.getReachableStates() && !maybeStates, infinityStates.template toAdd<ValueType>().ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), model.getManager().template getAddZero<ValueType>()), maybeStates, odd, x));
return std::unique_ptr<CheckResult>(new storm::modelchecker::HybridQuantitativeCheckResult<DdType>(model.getReachableStates(), model.getReachableStates() && !maybeStates, infinityStates.ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), model.getManager().template getAddZero<ValueType>()), maybeStates, odd, x));
} else {
return std::unique_ptr<CheckResult>(new storm::modelchecker::SymbolicQuantitativeCheckResult<DdType>(model.getReachableStates(), infinityStates.template toAdd<ValueType>().ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), model.getManager().template getAddZero<ValueType>())));
return std::unique_ptr<CheckResult>(new storm::modelchecker::SymbolicQuantitativeCheckResult<DdType>(model.getReachableStates(), infinityStates.ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), model.getManager().template getAddZero<ValueType>())));
}
}
}

6
src/modelchecker/prctl/helper/HybridMdpPrctlHelper.cpp

@ -218,7 +218,7 @@ namespace storm {
if (qualitative) {
// Set the values for all maybe-states to 1 to indicate that their reward values
// are neither 0 nor infinity.
return std::unique_ptr<CheckResult>(new SymbolicQuantitativeCheckResult<DdType>(model.getReachableStates(), infinityStates.template toAdd<ValueType>().ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), model.getManager().template getAddZero<ValueType>()) + maybeStates.template toAdd<ValueType>() * model.getManager().getConstant(storm::utility::one<ValueType>())));
return std::unique_ptr<CheckResult>(new SymbolicQuantitativeCheckResult<DdType>(model.getReachableStates(), infinityStates.ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), model.getManager().template getAddZero<ValueType>()) + maybeStates.template toAdd<ValueType>() * model.getManager().getConstant(storm::utility::one<ValueType>())));
} else {
// If there are maybe states, we need to solve an equation system.
if (!maybeStates.isZero()) {
@ -253,9 +253,9 @@ namespace storm {
solver->solveEquationSystem(dir, x, explicitRepresentation.second);
// Return a hybrid check result that stores the numerical values explicitly.
return std::unique_ptr<CheckResult>(new storm::modelchecker::HybridQuantitativeCheckResult<DdType>(model.getReachableStates(), model.getReachableStates() && !maybeStates, infinityStates.template toAdd<ValueType>().ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), model.getManager().template getAddZero<ValueType>()), maybeStates, odd, x));
return std::unique_ptr<CheckResult>(new storm::modelchecker::HybridQuantitativeCheckResult<DdType>(model.getReachableStates(), model.getReachableStates() && !maybeStates, infinityStates.ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), model.getManager().template getAddZero<ValueType>()), maybeStates, odd, x));
} else {
return std::unique_ptr<CheckResult>(new storm::modelchecker::SymbolicQuantitativeCheckResult<DdType>(model.getReachableStates(), infinityStates.template toAdd<ValueType>().ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), model.getManager().template getAddZero<ValueType>())));
return std::unique_ptr<CheckResult>(new storm::modelchecker::SymbolicQuantitativeCheckResult<DdType>(model.getReachableStates(), infinityStates.ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), model.getManager().template getAddZero<ValueType>())));
}
}
}

6
src/modelchecker/prctl/helper/SymbolicDtmcPrctlHelper.cpp

@ -147,7 +147,7 @@ namespace storm {
if (qualitative) {
// Set the values for all maybe-states to 1 to indicate that their reward values
// are neither 0 nor infinity.
return infinityStates.template toAdd<ValueType>().ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), model.getManager().template getAddZero<ValueType>()) + maybeStates.template toAdd<ValueType>() * model.getManager().getConstant(storm::utility::one<ValueType>());
return infinityStates.ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), model.getManager().template getAddZero<ValueType>()) + maybeStates.template toAdd<ValueType>() * model.getManager().getConstant(storm::utility::one<ValueType>());
} else {
// If there are maybe states, we need to solve an equation system.
if (!maybeStates.isZero()) {
@ -170,9 +170,9 @@ namespace storm {
std::unique_ptr<storm::solver::SymbolicLinearEquationSolver<DdType, ValueType>> solver = linearEquationSolverFactory.create(submatrix, maybeStates, model.getRowVariables(), model.getColumnVariables(), model.getRowColumnMetaVariablePairs());
storm::dd::Add<DdType, ValueType> result = solver->solveEquationSystem(model.getManager().getConstant(0.5) * maybeStatesAdd, subvector);
return infinityStates.template toAdd<ValueType>().ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), result);
return infinityStates.ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), result);
} else {
return infinityStates.template toAdd<ValueType>().ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), model.getManager().getConstant(storm::utility::zero<ValueType>()));
return infinityStates.ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), model.getManager().getConstant(storm::utility::zero<ValueType>()));
}
}
}

6
src/modelchecker/prctl/helper/SymbolicMdpPrctlHelper.cpp

@ -171,7 +171,7 @@ namespace storm {
if (qualitative) {
// Set the values for all maybe-states to 1 to indicate that their reward values
// are neither 0 nor infinity.
return std::unique_ptr<CheckResult>(new SymbolicQuantitativeCheckResult<DdType>(model.getReachableStates(), infinityStates.template toAdd<ValueType>().ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), model.getManager().template getAddZero<ValueType>()) + maybeStates.template toAdd<ValueType>() * model.getManager().getConstant(storm::utility::one<ValueType>())));
return std::unique_ptr<CheckResult>(new SymbolicQuantitativeCheckResult<DdType>(model.getReachableStates(), infinityStates.ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), model.getManager().template getAddZero<ValueType>()) + maybeStates.template toAdd<ValueType>() * model.getManager().getConstant(storm::utility::one<ValueType>())));
} else {
// If there are maybe states, we need to solve an equation system.
if (!maybeStates.isZero()) {
@ -192,9 +192,9 @@ namespace storm {
std::unique_ptr<storm::solver::SymbolicMinMaxLinearEquationSolver<DdType, ValueType>> solver = linearEquationSolverFactory.create(submatrix, maybeStates, model.getIllegalMask() && maybeStates, model.getRowVariables(), model.getColumnVariables(), model.getNondeterminismVariables(), model.getRowColumnMetaVariablePairs());
storm::dd::Add<DdType, ValueType> result = solver->solveEquationSystem(minimize, model.getManager().template getAddZero<ValueType>(), subvector);
return std::unique_ptr<CheckResult>(new storm::modelchecker::SymbolicQuantitativeCheckResult<DdType>(model.getReachableStates(), infinityStates.template toAdd<ValueType>().ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), result)));
return std::unique_ptr<CheckResult>(new storm::modelchecker::SymbolicQuantitativeCheckResult<DdType>(model.getReachableStates(), infinityStates.ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), result)));
} else {
return std::unique_ptr<CheckResult>(new storm::modelchecker::SymbolicQuantitativeCheckResult<DdType>(model.getReachableStates(), infinityStates.template toAdd<ValueType>().ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), model.getManager().template getAddZero<ValueType>())));
return std::unique_ptr<CheckResult>(new storm::modelchecker::SymbolicQuantitativeCheckResult<DdType>(model.getReachableStates(), infinityStates.ite(model.getManager().getConstant(storm::utility::infinity<ValueType>()), model.getManager().template getAddZero<ValueType>())));
}
}
}

2
src/modelchecker/results/HybridQuantitativeCheckResult.cpp

@ -143,7 +143,7 @@ namespace storm {
ValueType HybridQuantitativeCheckResult<Type, ValueType>::getMin() const {
// In order to not get false zeros, we need to set the values of all states whose values is not stored
// symbolically to infinity.
storm::dd::Add<Type, ValueType> tmp = symbolicStates.template toAdd<ValueType>().ite(this->symbolicValues, reachableStates.getDdManager().getConstant(storm::utility::infinity<double>()));
storm::dd::Add<Type, ValueType> tmp = symbolicStates.ite(this->symbolicValues, reachableStates.getDdManager().getConstant(storm::utility::infinity<double>()));
ValueType min = tmp.getMin();
if (!explicitStates.isZero()) {
for (auto const& element : explicitValues) {

2
src/modelchecker/results/SymbolicQuantitativeCheckResult.cpp

@ -81,7 +81,7 @@ namespace storm {
ValueType SymbolicQuantitativeCheckResult<Type, ValueType>::getMin() const {
// In order to not get false zeros, we need to set the values of all states whose values is not stored
// symbolically to infinity.
return states.template toAdd<ValueType>().ite(this->values, states.getDdManager().getConstant(storm::utility::infinity<double>())).getMin();
return states.ite(this->values, states.getDdManager().getConstant(storm::utility::infinity<double>())).getMin();
}
template<storm::dd::DdType Type, typename ValueType>

11
src/solver/SymbolicLinearEquationSolver.cpp

@ -28,15 +28,16 @@ namespace storm {
template<storm::dd::DdType DdType, typename ValueType>
storm::dd::Add<DdType, ValueType> SymbolicLinearEquationSolver<DdType, ValueType>::solveEquationSystem(storm::dd::Add<DdType, ValueType> const& x, storm::dd::Add<DdType, ValueType> const& b) const {
// Start by computing the Jacobi decomposition of the matrix A.
storm::dd::Add<DdType, ValueType> diagonal = x.getDdManager().template getAddOne<ValueType>();
storm::dd::Bdd<DdType> diagonal = x.getDdManager().getBddOne();
for (auto const& pair : rowColumnMetaVariablePairs) {
diagonal *= x.getDdManager().template getIdentity<ValueType>(pair.first).equals(x.getDdManager().template getIdentity<ValueType>(pair.second)).template toAdd<ValueType>();
diagonal *= x.getDdManager().getRange(pair.first).template toAdd<ValueType>() * x.getDdManager().getRange(pair.second).template toAdd<ValueType>();
diagonal &= x.getDdManager().template getIdentity<ValueType>(pair.first).equals(x.getDdManager().template getIdentity<ValueType>(pair.second));
diagonal &= x.getDdManager().getRange(pair.first) && x.getDdManager().getRange(pair.second);
}
diagonal *= allRows.template toAdd<ValueType>();
diagonal &= allRows;
storm::dd::Add<DdType, ValueType> lu = diagonal.ite(this->A.getDdManager().template getAddZero<ValueType>(), this->A);
storm::dd::Add<DdType, ValueType> dinv = diagonal / (diagonal * this->A);
storm::dd::Add<DdType> diagonalAdd = diagonal.template toAdd<ValueType>();
storm::dd::Add<DdType, ValueType> dinv = diagonalAdd / (diagonalAdd * this->A);
// Set up additional environment variables.
storm::dd::Add<DdType, ValueType> xCopy = x;

4
src/solver/SymbolicMinMaxLinearEquationSolver.cpp

@ -14,12 +14,12 @@ namespace storm {
namespace solver {
template<storm::dd::DdType DdType, typename ValueType>
SymbolicMinMaxLinearEquationSolver<DdType, ValueType>::SymbolicMinMaxLinearEquationSolver(storm::dd::Add<DdType, ValueType> const& A, storm::dd::Bdd<DdType> const& allRows, storm::dd::Bdd<DdType> const& illegalMask, std::set<storm::expressions::Variable> const& rowMetaVariables, std::set<storm::expressions::Variable> const& columnMetaVariables, std::set<storm::expressions::Variable> const& choiceVariables, std::vector<std::pair<storm::expressions::Variable, storm::expressions::Variable>> const& rowColumnMetaVariablePairs, double precision, uint_fast64_t maximalNumberOfIterations, bool relative) : A(A), allRows(allRows), illegalMaskAdd(illegalMask.template toAdd<ValueType>().ite(A.getDdManager().getConstant(storm::utility::infinity<ValueType>()), A.getDdManager().template getAddZero<ValueType>())), rowMetaVariables(rowMetaVariables), columnMetaVariables(columnMetaVariables), choiceVariables(choiceVariables), rowColumnMetaVariablePairs(rowColumnMetaVariablePairs), precision(precision), maximalNumberOfIterations(maximalNumberOfIterations), relative(relative) {
SymbolicMinMaxLinearEquationSolver<DdType, ValueType>::SymbolicMinMaxLinearEquationSolver(storm::dd::Add<DdType, ValueType> const& A, storm::dd::Bdd<DdType> const& allRows, storm::dd::Bdd<DdType> const& illegalMask, std::set<storm::expressions::Variable> const& rowMetaVariables, std::set<storm::expressions::Variable> const& columnMetaVariables, std::set<storm::expressions::Variable> const& choiceVariables, std::vector<std::pair<storm::expressions::Variable, storm::expressions::Variable>> const& rowColumnMetaVariablePairs, double precision, uint_fast64_t maximalNumberOfIterations, bool relative) : A(A), allRows(allRows), illegalMaskAdd(illegalMask.ite(A.getDdManager().getConstant(storm::utility::infinity<ValueType>()), A.getDdManager().template getAddZero<ValueType>())), rowMetaVariables(rowMetaVariables), columnMetaVariables(columnMetaVariables), choiceVariables(choiceVariables), rowColumnMetaVariablePairs(rowColumnMetaVariablePairs), precision(precision), maximalNumberOfIterations(maximalNumberOfIterations), relative(relative) {
// Intentionally left empty.
}
template<storm::dd::DdType DdType, typename ValueType>
SymbolicMinMaxLinearEquationSolver<DdType, ValueType>::SymbolicMinMaxLinearEquationSolver(storm::dd::Add<DdType, ValueType> const& A, storm::dd::Bdd<DdType> const& allRows, storm::dd::Bdd<DdType> const& illegalMask, std::set<storm::expressions::Variable> const& rowMetaVariables, std::set<storm::expressions::Variable> const& columnMetaVariables, std::set<storm::expressions::Variable> const& choiceVariables, std::vector<std::pair<storm::expressions::Variable, storm::expressions::Variable>> const& rowColumnMetaVariablePairs) : A(A), allRows(allRows), illegalMaskAdd(illegalMask.template toAdd<ValueType>().ite(A.getDdManager().getConstant(storm::utility::infinity<ValueType>()), A.getDdManager().template getAddZero<ValueType>())), rowMetaVariables(rowMetaVariables), columnMetaVariables(columnMetaVariables), choiceVariables(choiceVariables), rowColumnMetaVariablePairs(rowColumnMetaVariablePairs) {
SymbolicMinMaxLinearEquationSolver<DdType, ValueType>::SymbolicMinMaxLinearEquationSolver(storm::dd::Add<DdType, ValueType> const& A, storm::dd::Bdd<DdType> const& allRows, storm::dd::Bdd<DdType> const& illegalMask, std::set<storm::expressions::Variable> const& rowMetaVariables, std::set<storm::expressions::Variable> const& columnMetaVariables, std::set<storm::expressions::Variable> const& choiceVariables, std::vector<std::pair<storm::expressions::Variable, storm::expressions::Variable>> const& rowColumnMetaVariablePairs) : A(A), allRows(allRows), illegalMaskAdd(illegalMask.ite(A.getDdManager().getConstant(storm::utility::infinity<ValueType>()), A.getDdManager().template getAddZero<ValueType>())), rowMetaVariables(rowMetaVariables), columnMetaVariables(columnMetaVariables), choiceVariables(choiceVariables), rowColumnMetaVariablePairs(rowColumnMetaVariablePairs) {
// Get the settings object to customize solving.
storm::settings::modules::NativeEquationSolverSettings const& settings = storm::settings::nativeEquationSolverSettings();

9
src/storage/dd/Add.cpp

@ -29,13 +29,6 @@ namespace storm {
return internalAdd != other.internalAdd;
}
template<DdType LibraryType, typename ValueType>
Add<LibraryType, ValueType> Add<LibraryType, ValueType>::ite(Add<LibraryType, ValueType> const& thenAdd, Add<LibraryType, ValueType> const& elseAdd) const {
std::set<storm::expressions::Variable> metaVariables = Dd<LibraryType>::joinMetaVariables(thenAdd, elseAdd);
metaVariables.insert(this->getContainedMetaVariables().begin(), this->getContainedMetaVariables().end());
return Add<LibraryType, ValueType>(this->getDdManager(), internalAdd.ite(thenAdd.internalAdd, elseAdd.internalAdd), metaVariables);
}
template<DdType LibraryType, typename ValueType>
Add<LibraryType, ValueType> Add<LibraryType, ValueType>::operator+(Add<LibraryType, ValueType> const& other) const {
return Add<LibraryType, ValueType>(this->getDdManager(), internalAdd + other.internalAdd, Dd<LibraryType>::joinMetaVariables(*this, other));
@ -320,7 +313,7 @@ namespace storm {
this->addMetaVariable(nameValuePair.first);
}
internalAdd = valueEncoding.template toAdd<ValueType>().ite(this->getDdManager().getConstant(targetValue), *this);
internalAdd = valueEncoding.ite(this->getDdManager().getConstant(targetValue), *this);
}
template<DdType LibraryType, typename ValueType>

11
src/storage/dd/Add.h

@ -65,17 +65,6 @@ namespace storm {
*/
bool operator!=(Add<LibraryType, ValueType> const& other) const;
/*!
* Performs an if-then-else with the given operands, i.e. maps all valuations that are mapped to a non-zero
* function value to the function values specified by the first DD and all others to the function values
* specified by the second DD.
*
* @param thenDd The ADD specifying the 'then' part.
* @param elseDd The ADD specifying the 'else' part.
* @return The ADD corresponding to the if-then-else of the operands.
*/
Add<LibraryType, ValueType> ite(Add<LibraryType, ValueType> const& thenAdd, Add<LibraryType, ValueType> const& elseAdd) const;
/*!
* Adds the two ADDs.
*

14
src/storage/dd/Bdd.cpp

@ -58,6 +58,14 @@ namespace storm {
return Bdd<LibraryType>(this->getDdManager(), internalBdd.ite(thenBdd.internalBdd, elseBdd.internalBdd), metaVariables);
}
template<DdType LibraryType>
template<typename ValueType>
Add<LibraryType, ValueType> Bdd<LibraryType>::ite(Add<LibraryType, ValueType> const& thenAdd, Add<LibraryType, ValueType> const& elseAdd) const {
std::set<storm::expressions::Variable> metaVariables = Dd<LibraryType>::joinMetaVariables(thenAdd, elseAdd);
metaVariables.insert(this->getContainedMetaVariables().begin(), this->getContainedMetaVariables().end());
return Add<LibraryType, ValueType>(this->getDdManager(), internalBdd.ite(thenAdd.internalAdd, elseAdd.internalAdd), metaVariables);
}
template<DdType LibraryType>
Bdd<LibraryType> Bdd<LibraryType>::operator||(Bdd<LibraryType> const& other) const {
return Bdd<LibraryType>(this->getDdManager(), internalBdd || other.internalBdd, Dd<LibraryType>::joinMetaVariables(*this, other));
@ -334,6 +342,9 @@ namespace storm {
template std::vector<double> Bdd<DdType::CUDD>::filterExplicitVector(Odd const& odd, std::vector<double> const& values) const;
template std::vector<uint_fast64_t> Bdd<DdType::CUDD>::filterExplicitVector(Odd const& odd, std::vector<uint_fast64_t> const& values) const;
template Add<DdType::CUDD, double> Bdd<DdType::CUDD>::ite(Add<DdType::CUDD, double> const& thenAdd, Add<DdType::CUDD, double> const& elseAdd) const;
template Add<DdType::CUDD, uint_fast64_t> Bdd<DdType::CUDD>::ite(Add<DdType::CUDD, uint_fast64_t> const& thenAdd, Add<DdType::CUDD, uint_fast64_t> const& elseAdd) const;
template class Bdd<DdType::Sylvan>;
@ -345,5 +356,8 @@ namespace storm {
template std::vector<double> Bdd<DdType::Sylvan>::filterExplicitVector(Odd const& odd, std::vector<double> const& values) const;
template std::vector<uint_fast64_t> Bdd<DdType::Sylvan>::filterExplicitVector(Odd const& odd, std::vector<uint_fast64_t> const& values) const;
template Add<DdType::Sylvan, double> Bdd<DdType::Sylvan>::ite(Add<DdType::Sylvan, double> const& thenAdd, Add<DdType::Sylvan, double> const& elseAdd) const;
template Add<DdType::Sylvan, uint_fast64_t> Bdd<DdType::Sylvan>::ite(Add<DdType::Sylvan, uint_fast64_t> const& thenAdd, Add<DdType::Sylvan, uint_fast64_t> const& elseAdd) const;
}
}

11
src/storage/dd/Bdd.h

@ -74,6 +74,17 @@ namespace storm {
*/
Bdd<LibraryType> ite(Bdd<LibraryType> const& thenBdd, Bdd<LibraryType> const& elseBdd) const;
/*!
* Performs an if-then-else with the given operands, i.e. maps all valuations that are mapped to true to the
* function values specified by the first DD and all others to the function values specified by the second DD.
*
* @param thenAdd The ADD defining the 'then' part.
* @param elseAdd The ADD defining the 'else' part.
* @return The resulting ADD.
*/
template<typename ValueType>
Add<LibraryType, ValueType> ite(Add<LibraryType, ValueType> const& thenAdd, Add<LibraryType, ValueType> const& elseAdd) const;
/*!
* Performs a logical or of the current and the given BDD.
*

7
src/storage/dd/cudd/InternalCuddAdd.cpp

@ -26,12 +26,7 @@ namespace storm {
bool InternalAdd<DdType::CUDD, ValueType>::operator!=(InternalAdd<DdType::CUDD, ValueType> const& other) const {
return !(*this == other);
}
template<typename ValueType>
InternalAdd<DdType::CUDD, ValueType> InternalAdd<DdType::CUDD, ValueType>::ite(InternalAdd<DdType::CUDD, ValueType> const& thenDd, InternalAdd<DdType::CUDD, ValueType> const& elseDd) const {
return InternalAdd<DdType::CUDD, ValueType>(ddManager, this->getCuddAdd().Ite(thenDd.getCuddAdd(), elseDd.getCuddAdd()));
}
template<typename ValueType>
InternalAdd<DdType::CUDD, ValueType> InternalAdd<DdType::CUDD, ValueType>::operator+(InternalAdd<DdType::CUDD, ValueType> const& other) const {
return InternalAdd<DdType::CUDD, ValueType>(ddManager, this->getCuddAdd() + other.getCuddAdd());

13
src/storage/dd/cudd/InternalCuddAdd.h

@ -42,6 +42,8 @@ namespace storm {
template<typename ValueType>
class InternalAdd<DdType::CUDD, ValueType> {
public:
friend class InternalBdd<DdType::CUDD>;
/*!
* Creates an ADD that encapsulates the given CUDD ADD.
*
@ -73,17 +75,6 @@ namespace storm {
*/
bool operator!=(InternalAdd<DdType::CUDD, ValueType> const& other) const;
/*!
* Performs an if-then-else with the given operands, i.e. maps all valuations that are mapped to a non-zero
* function value to the function values specified by the first DD and all others to the function values
* specified by the second DD.
*
* @param thenDd The ADD specifying the 'then' part.
* @param elseDd The ADD specifying the 'else' part.
* @return The ADD corresponding to the if-then-else of the operands.
*/
InternalAdd<DdType::CUDD, ValueType> ite(InternalAdd<DdType::CUDD, ValueType> const& thenAdd, InternalAdd<DdType::CUDD, ValueType> const& elseAdd) const;
/*!
* Adds the two ADDs.
*

8
src/storage/dd/cudd/InternalCuddBdd.cpp

@ -58,6 +58,11 @@ namespace storm {
return InternalBdd<DdType::CUDD>(ddManager, this->getCuddBdd().Ite(thenDd.getCuddBdd(), elseDd.getCuddBdd()));
}
template<typename ValueType>
InternalAdd<DdType::CUDD, ValueType> InternalBdd<DdType::CUDD>::ite(InternalAdd<DdType::CUDD, ValueType> const& thenAdd, InternalAdd<DdType::CUDD, ValueType> const& elseAdd) const {
return InternalAdd<DdType::CUDD, ValueType>(ddManager, this->getCuddBdd().Add().Ite(thenAdd.getCuddAdd(), elseAdd.getCuddAdd()));
}
InternalBdd<DdType::CUDD> InternalBdd<DdType::CUDD>::operator||(InternalBdd<DdType::CUDD> const& other) const {
InternalBdd<DdType::CUDD> result(*this);
result |= other;
@ -413,5 +418,8 @@ namespace storm {
template void InternalBdd<DdType::CUDD>::filterExplicitVector(Odd const& odd, std::vector<uint_fast64_t> const& ddVariableIndices, std::vector<double> const& sourceValues, std::vector<double>& targetValues) const;
template void InternalBdd<DdType::CUDD>::filterExplicitVector(Odd const& odd, std::vector<uint_fast64_t> const& ddVariableIndices, std::vector<uint_fast64_t> const& sourceValues, std::vector<uint_fast64_t>& targetValues) const;
template InternalAdd<DdType::CUDD, double> InternalBdd<DdType::CUDD>::ite(InternalAdd<DdType::CUDD, double> const& thenAdd, InternalAdd<DdType::CUDD, double> const& elseAdd) const;
template InternalAdd<DdType::CUDD, uint_fast64_t> InternalBdd<DdType::CUDD>::ite(InternalAdd<DdType::CUDD, uint_fast64_t> const& thenAdd, InternalAdd<DdType::CUDD, uint_fast64_t> const& elseAdd) const;
}
}

11
src/storage/dd/cudd/InternalCuddBdd.h

@ -120,6 +120,17 @@ namespace storm {
*/
InternalBdd<DdType::CUDD> ite(InternalBdd<DdType::CUDD> const& thenBdd, InternalBdd<DdType::CUDD> const& elseBdd) const;
/*!
* Performs an if-then-else with the given operands, i.e. maps all valuations that are mapped to true to the
* function values specified by the first DD and all others to the function values specified by the second DD.
*
* @param thenAdd The ADD defining the 'then' part.
* @param elseAdd The ADD defining the 'else' part.
* @return The resulting ADD.
*/
template<typename ValueType>
InternalAdd<DdType::CUDD, ValueType> ite(InternalAdd<DdType::CUDD, ValueType> const& thenAdd, InternalAdd<DdType::CUDD, ValueType> const& elseAdd) const;
/*!
* Performs a logical or of the current and the given BDD.
*

7
src/storage/dd/sylvan/InternalSylvanAdd.cpp

@ -26,12 +26,7 @@ namespace storm {
bool InternalAdd<DdType::Sylvan, ValueType>::operator!=(InternalAdd<DdType::Sylvan, ValueType> const& other) const {
return this->sylvanMtbdd != other.sylvanMtbdd;
}
template<typename ValueType>
InternalAdd<DdType::Sylvan, ValueType> InternalAdd<DdType::Sylvan, ValueType>::ite(InternalAdd<DdType::Sylvan, ValueType> const& thenDd, InternalAdd<DdType::Sylvan, ValueType> const& elseDd) const {
return InternalAdd<DdType::Sylvan, ValueType>(ddManager, sylvan::Mtbdd(static_cast<MTBDD>(this->sylvanMtbdd.NotZero().GetBDD())).Ite(thenDd.sylvanMtbdd, elseDd.sylvanMtbdd));
}
template<typename ValueType>
InternalAdd<DdType::Sylvan, ValueType> InternalAdd<DdType::Sylvan, ValueType>::operator+(InternalAdd<DdType::Sylvan, ValueType> const& other) const {
return InternalAdd<DdType::Sylvan, ValueType>(ddManager, this->sylvanMtbdd.Plus(other.sylvanMtbdd));

12
src/storage/dd/sylvan/InternalSylvanAdd.h

@ -41,6 +41,7 @@ namespace storm {
class InternalAdd<DdType::Sylvan, ValueType> {
public:
friend class AddIterator<DdType::Sylvan, ValueType>;
friend class InternalBdd<DdType::Sylvan>;
/*!
* Creates an ADD that encapsulates the given Sylvan MTBDD.
@ -72,17 +73,6 @@ namespace storm {
* @return True if the DDs represent the different functions.
*/
bool operator!=(InternalAdd<DdType::Sylvan, ValueType> const& other) const;
/*!
* Performs an if-then-else with the given operands, i.e. maps all valuations that are mapped to a non-zero
* function value to the function values specified by the first DD and all others to the function values
* specified by the second DD.
*
* @param thenDd The ADD specifying the 'then' part.
* @param elseDd The ADD specifying the 'else' part.
* @return The ADD corresponding to the if-then-else of the operands.
*/
InternalAdd<DdType::Sylvan, ValueType> ite(InternalAdd<DdType::Sylvan, ValueType> const& thenAdd, InternalAdd<DdType::Sylvan, ValueType> const& elseAdd) const;
/*!
* Adds the two ADDs.

9
src/storage/dd/sylvan/InternalSylvanBdd.cpp

@ -107,6 +107,11 @@ namespace storm {
return InternalBdd<DdType::Sylvan>(ddManager, this->sylvanBdd.Ite(thenDd.sylvanBdd, elseDd.sylvanBdd));
}
template<typename ValueType>
InternalAdd<DdType::Sylvan, ValueType> InternalBdd<DdType::Sylvan>::ite(InternalAdd<DdType::Sylvan, ValueType> const& thenAdd, InternalAdd<DdType::Sylvan, ValueType> const& elseAdd) const {
return InternalAdd<DdType::Sylvan, ValueType>(ddManager, this->sylvanBdd.Ite(thenAdd.getSylvanMtbdd(), elseAdd.getSylvanMtbdd()));
}
InternalBdd<DdType::Sylvan> InternalBdd<DdType::Sylvan>::operator||(InternalBdd<DdType::Sylvan> const& other) const {
return InternalBdd<DdType::Sylvan>(ddManager, this->sylvanBdd | other.sylvanBdd);
}
@ -382,5 +387,9 @@ namespace storm {
template void InternalBdd<DdType::Sylvan>::filterExplicitVector(Odd const& odd, std::vector<uint_fast64_t> const& ddVariableIndices, std::vector<double> const& sourceValues, std::vector<double>& targetValues) const;
template void InternalBdd<DdType::Sylvan>::filterExplicitVector(Odd const& odd, std::vector<uint_fast64_t> const& ddVariableIndices, std::vector<uint_fast64_t> const& sourceValues, std::vector<uint_fast64_t>& targetValues) const;
template InternalAdd<DdType::Sylvan, double> InternalBdd<DdType::Sylvan>::ite(InternalAdd<DdType::Sylvan, double> const& thenAdd, InternalAdd<DdType::Sylvan, double> const& elseAdd) const;
template InternalAdd<DdType::Sylvan, uint_fast64_t> InternalBdd<DdType::Sylvan>::ite(InternalAdd<DdType::Sylvan, uint_fast64_t> const& thenAdd, InternalAdd<DdType::Sylvan, uint_fast64_t> const& elseAdd) const;
}
}

11
src/storage/dd/sylvan/InternalSylvanBdd.h

@ -108,6 +108,17 @@ namespace storm {
*/
InternalBdd<DdType::Sylvan> ite(InternalBdd<DdType::Sylvan> const& thenBdd, InternalBdd<DdType::Sylvan> const& elseBdd) const;
/*!
* Performs an if-then-else with the given operands, i.e. maps all valuations that are mapped to true to the
* function values specified by the first DD and all others to the function values specified by the second DD.
*
* @param thenAdd The ADD defining the 'then' part.
* @param elseAdd The ADD defining the 'else' part.
* @return The resulting ADD.
*/
template<typename ValueType>
InternalAdd<DdType::Sylvan, ValueType> ite(InternalAdd<DdType::Sylvan, ValueType> const& thenAdd, InternalAdd<DdType::Sylvan, ValueType> const& elseAdd) const;
/*!
* Performs a logical or of the current and the given BDD.
*

8
test/functional/storage/CuddDdTest.cpp

@ -164,7 +164,7 @@ TEST(CuddDd, OperatorTest) {
dd3 = dd1.greaterOrEqual(dd2).template toAdd<double>();
EXPECT_EQ(5ul, dd3.getNonZeroCount());
dd3 = (manager->getEncoding(x.first, 2).template toAdd<double>()).ite(dd2, dd1);
dd3 = manager->getEncoding(x.first, 2).ite(dd2, dd1);
dd4 = dd3.less(dd2).template toAdd<double>();
EXPECT_EQ(10ul, dd4.getNonZeroCount());
@ -296,7 +296,7 @@ TEST(CuddDd, AddIteratorTest) {
EXPECT_EQ(9ul, numberOfValuations);
dd = manager->getRange(x.first).template toAdd<double>();
dd = dd.ite(manager->template getAddOne<double>(), manager->template getAddOne<double>());
dd = dd.notZero().ite(manager->template getAddOne<double>(), manager->template getAddOne<double>());
ASSERT_NO_THROW(it = dd.begin());
ASSERT_NO_THROW(ite = dd.end());
numberOfValuations = 0;
@ -354,7 +354,7 @@ TEST(CuddDd, AddOddTest) {
EXPECT_EQ(9ul, matrix.getColumnCount());
EXPECT_EQ(25ul, matrix.getNonzeroEntryCount());
dd = manager->getRange(x.first).template toAdd<double>() * manager->getRange(x.second).template toAdd<double>() * manager->getEncoding(a.first, 0).template toAdd<double>().ite(dd, dd + manager->template getConstant<double>(1));
dd = manager->getRange(x.first).template toAdd<double>() * manager->getRange(x.second).template toAdd<double>() * manager->getEncoding(a.first, 0).ite(dd, dd + manager->template getConstant<double>(1));
ASSERT_NO_THROW(matrix = dd.toMatrix({a.first}, rowOdd, columnOdd));
EXPECT_EQ(18ul, matrix.getRowCount());
EXPECT_EQ(9ul, matrix.getRowGroupCount());
@ -401,7 +401,7 @@ TEST(CuddDd, BddOddTest) {
EXPECT_EQ(9ul, matrix.getColumnCount());
EXPECT_EQ(25ul, matrix.getNonzeroEntryCount());
dd = manager->getRange(x.first).template toAdd<double>() * manager->getRange(x.second).template toAdd<double>() * manager->getEncoding(a.first, 0).template toAdd<double>().ite(dd, dd + manager->template getConstant<double>(1));
dd = manager->getRange(x.first).template toAdd<double>() * manager->getRange(x.second).template toAdd<double>() * manager->getEncoding(a.first, 0).ite(dd, dd + manager->template getConstant<double>(1));
ASSERT_NO_THROW(matrix = dd.toMatrix({a.first}, rowOdd, columnOdd));
EXPECT_EQ(18ul, matrix.getRowCount());
EXPECT_EQ(9ul, matrix.getRowGroupCount());

8
test/functional/storage/SylvanDdTest.cpp

@ -168,7 +168,7 @@ TEST(SylvanDd, OperatorTest) {
bdd = dd1.greaterOrEqual(dd2);
EXPECT_EQ(5ul, bdd.getNonZeroCount());
dd3 = (manager->getEncoding(x.first, 2).template toAdd<double>()).ite(dd2, dd1);
dd3 = manager->getEncoding(x.first, 2).ite(dd2, dd1);
bdd = dd3.less(dd2);
EXPECT_EQ(10ul, bdd.getNonZeroCount());
@ -300,7 +300,7 @@ TEST(SylvanDd, AddIteratorTest) {
EXPECT_EQ(9ul, numberOfValuations);
dd = manager->getRange(x.first).template toAdd<double>();
dd = dd.ite(manager->template getAddOne<double>(), manager->template getAddOne<double>());
dd = dd.notZero().ite(manager->template getAddOne<double>(), manager->template getAddOne<double>());
ASSERT_NO_THROW(it = dd.begin());
ASSERT_NO_THROW(ite = dd.end());
numberOfValuations = 0;
@ -358,7 +358,7 @@ TEST(SylvanDd, AddOddTest) {
EXPECT_EQ(9ul, matrix.getColumnCount());
EXPECT_EQ(25ul, matrix.getNonzeroEntryCount());
dd = manager->getRange(x.first).template toAdd<double>() * manager->getRange(x.second).template toAdd<double>() * manager->getEncoding(a.first, 0).template toAdd<double>().ite(dd, dd + manager->template getConstant<double>(1));
dd = manager->getRange(x.first).template toAdd<double>() * manager->getRange(x.second).template toAdd<double>() * manager->getEncoding(a.first, 0).ite(dd, dd + manager->template getConstant<double>(1));
ASSERT_NO_THROW(matrix = dd.toMatrix({a.first}, rowOdd, columnOdd));
EXPECT_EQ(18ul, matrix.getRowCount());
EXPECT_EQ(9ul, matrix.getRowGroupCount());
@ -405,7 +405,7 @@ TEST(SylvanDd, BddOddTest) {
EXPECT_EQ(9ul, matrix.getColumnCount());
EXPECT_EQ(25ul, matrix.getNonzeroEntryCount());
dd = manager->getRange(x.first).template toAdd<double>() * manager->getRange(x.second).template toAdd<double>() * manager->getEncoding(a.first, 0).template toAdd<double>().ite(dd, dd + manager->template getConstant<double>(1));
dd = manager->getRange(x.first).template toAdd<double>() * manager->getRange(x.second).template toAdd<double>() * manager->getEncoding(a.first, 0).ite(dd, dd + manager->template getConstant<double>(1));
ASSERT_NO_THROW(matrix = dd.toMatrix({a.first}, rowOdd, columnOdd));
EXPECT_EQ(18ul, matrix.getRowCount());
EXPECT_EQ(9ul, matrix.getRowGroupCount());

Loading…
Cancel
Save