You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

292 lines
17 KiB

  1. #include "gtest/gtest.h"
  2. #include "storm-config.h"
  3. #include "src/logic/Formulas.h"
  4. #include "src/utility/solver.h"
  5. #include "src/modelchecker/prctl/SparseMdpPrctlModelChecker.h"
  6. #include "src/modelchecker/results/ExplicitQuantitativeCheckResult.h"
  7. #include "src/settings/SettingsManager.h"
  8. #include "src/settings/SettingMemento.h"
  9. #include "src/parser/AutoParser.h"
  10. #include "storm-config.h"
  11. TEST(TopologicalValueIterationMdpPrctlModelCheckerTest, Dice) {
  12. //storm::settings::Settings* s = storm::settings::Settings::getInstance();
  13. std::shared_ptr<storm::models::sparse::Mdp<double>> mdp = storm::parser::AutoParser::parseModel(STORM_CPP_BASE_PATH "/examples/mdp/two_dice/two_dice.tra", STORM_CPP_BASE_PATH "/examples/mdp/two_dice/two_dice.lab", "", STORM_CPP_BASE_PATH "/examples/mdp/two_dice/two_dice.flip.trans.rew")->as<storm::models::sparse::Mdp<double>>();
  14. ASSERT_EQ(mdp->getNumberOfStates(), 169ull);
  15. ASSERT_EQ(mdp->getNumberOfTransitions(), 436ull);
  16. storm::modelchecker::SparseMdpPrctlModelChecker<double> mc(*mdp, std::unique_ptr<storm::utility::solver::MinMaxLinearEquationSolverFactory<double>>(new storm::utility::solver::TopologicalMinMaxLinearEquationSolverFactory<double>()));
  17. //storm::property::prctl::Ap<double>* apFormula = new storm::property::prctl::Ap<double>("two");
  18. auto apFormula = std::make_shared<storm::logic::AtomicLabelFormula>("two");
  19. //storm::property::prctl::Eventually<double>* eventuallyFormula = new storm::property::prctl::Eventually<double>(apFormula);
  20. auto eventuallyFormula = std::make_shared<storm::logic::EventuallyFormula>(apFormula);
  21. //storm::property::prctl::ProbabilisticNoBoundOperator<double>* probFormula = new storm::property::prctl::ProbabilisticNoBoundOperator<double>(eventuallyFormula, true);
  22. auto probabilityOperatorFormula = std::make_shared<storm::logic::ProbabilityOperatorFormula>(storm::logic::OptimalityType::Minimize, eventuallyFormula);
  23. //std::vector<double> result = mc.checkNoBoundOperator(*probFormula);
  24. std::unique_ptr<storm::modelchecker::CheckResult> result = mc.check(*probabilityOperatorFormula);
  25. //ASSERT_LT(std::abs(result[0] - 0.0277777612209320068), s->getOptionByLongName("precision").getArgument(0).getValueAsDouble());
  26. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 0.0277777612209320068),
  27. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  28. //delete probFormula;
  29. probabilityOperatorFormula.reset();
  30. //apFormula = new storm::property::prctl::Ap<double>("two");
  31. apFormula = std::make_shared<storm::logic::AtomicLabelFormula>("two");
  32. //eventuallyFormula = new storm::property::prctl::Eventually<double>(apFormula);
  33. eventuallyFormula = std::make_shared<storm::logic::EventuallyFormula>(apFormula);
  34. //probFormula = new storm::property::prctl::ProbabilisticNoBoundOperator<double>(eventuallyFormula, false);
  35. probabilityOperatorFormula = std::make_shared<storm::logic::ProbabilityOperatorFormula>(storm::logic::OptimalityType::Maximize, eventuallyFormula);
  36. //result = mc.checkNoBoundOperator(*probFormula);
  37. result = mc.check(*probabilityOperatorFormula);
  38. //ASSERT_LT(std::abs(result[0] - 0.0277777612209320068), s->getOptionByLongName("precision").getArgument(0).getValueAsDouble());
  39. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 0.0277777612209320068),
  40. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  41. //delete probFormula;
  42. probabilityOperatorFormula.reset();
  43. // ---------------- test ap "three" ----------------
  44. apFormula = std::make_shared<storm::logic::AtomicLabelFormula>("three");
  45. eventuallyFormula = std::make_shared<storm::logic::EventuallyFormula>(apFormula);
  46. probabilityOperatorFormula = std::make_shared<storm::logic::ProbabilityOperatorFormula>(storm::logic::OptimalityType::Minimize, eventuallyFormula);
  47. result = mc.check(*probabilityOperatorFormula);
  48. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 0.0555555224418640136),
  49. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  50. probabilityOperatorFormula.reset();
  51. apFormula = std::make_shared<storm::logic::AtomicLabelFormula>("three");
  52. eventuallyFormula = std::make_shared<storm::logic::EventuallyFormula>(apFormula);
  53. probabilityOperatorFormula = std::make_shared<storm::logic::ProbabilityOperatorFormula>(storm::logic::OptimalityType::Maximize, eventuallyFormula);
  54. result = mc.check(*probabilityOperatorFormula);
  55. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 0.0555555224418640136),
  56. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  57. probabilityOperatorFormula.reset();
  58. // ---------------- test ap "four" ----------------
  59. apFormula = std::make_shared<storm::logic::AtomicLabelFormula>("four");
  60. eventuallyFormula = std::make_shared<storm::logic::EventuallyFormula>(apFormula);
  61. probabilityOperatorFormula = std::make_shared<storm::logic::ProbabilityOperatorFormula>(storm::logic::OptimalityType::Minimize, eventuallyFormula);
  62. result = mc.check(*probabilityOperatorFormula);
  63. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 0.083333283662796020508),
  64. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  65. probabilityOperatorFormula.reset();
  66. apFormula = std::make_shared<storm::logic::AtomicLabelFormula>("four");
  67. eventuallyFormula = std::make_shared<storm::logic::EventuallyFormula>(apFormula);
  68. probabilityOperatorFormula = std::make_shared<storm::logic::ProbabilityOperatorFormula>(storm::logic::OptimalityType::Maximize, eventuallyFormula);
  69. result = mc.check(*probabilityOperatorFormula);
  70. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 0.083333283662796020508),
  71. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  72. probabilityOperatorFormula.reset();
  73. // ---------------- test ap "done" ----------------
  74. apFormula = std::make_shared<storm::logic::AtomicLabelFormula>("done");
  75. auto reachabilityRewardFormula = std::make_shared<storm::logic::ReachabilityRewardFormula>(apFormula);
  76. auto rewardFormula = std::make_shared<storm::logic::RewardOperatorFormula>(storm::logic::OptimalityType::Minimize, reachabilityRewardFormula);
  77. result = mc.check(*rewardFormula);
  78. #ifdef STORM_HAVE_CUDA
  79. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 7.333329499),
  80. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  81. #else
  82. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 7.33332904),
  83. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  84. #endif
  85. rewardFormula.reset();
  86. apFormula = std::make_shared<storm::logic::AtomicLabelFormula>("done");
  87. reachabilityRewardFormula = std::make_shared<storm::logic::ReachabilityRewardFormula>(apFormula);
  88. rewardFormula = std::make_shared<storm::logic::RewardOperatorFormula>(storm::logic::OptimalityType::Maximize, reachabilityRewardFormula);
  89. result = mc.check(*rewardFormula);
  90. #ifdef STORM_HAVE_CUDA
  91. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 7.333329499),
  92. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  93. #else
  94. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 7.33333151),
  95. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  96. #endif
  97. rewardFormula.reset();
  98. // ------------- state rewards --------------
  99. std::shared_ptr<storm::models::sparse::Mdp<double>> stateRewardMdp = storm::parser::AutoParser::parseModel(STORM_CPP_BASE_PATH "/examples/mdp/two_dice/two_dice.tra", STORM_CPP_BASE_PATH "/examples/mdp/two_dice/two_dice.lab", STORM_CPP_BASE_PATH "/examples/mdp/two_dice/two_dice.flip.state.rew", "")->as<storm::models::sparse::Mdp<double>>();
  100. storm::modelchecker::SparseMdpPrctlModelChecker<double> stateRewardModelChecker(*stateRewardMdp, std::unique_ptr<storm::utility::solver::MinMaxLinearEquationSolverFactory<double>>(new storm::utility::solver::TopologicalMinMaxLinearEquationSolverFactory<double>()));
  101. apFormula = std::make_shared<storm::logic::AtomicLabelFormula>("done");
  102. reachabilityRewardFormula = std::make_shared<storm::logic::ReachabilityRewardFormula>(apFormula);
  103. rewardFormula = std::make_shared<storm::logic::RewardOperatorFormula>(storm::logic::OptimalityType::Minimize, reachabilityRewardFormula);
  104. result = stateRewardModelChecker.check(*rewardFormula);
  105. #ifdef STORM_HAVE_CUDA
  106. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 7.333329499),
  107. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  108. #else
  109. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 7.33332904),
  110. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  111. #endif
  112. rewardFormula.reset();
  113. apFormula = std::make_shared<storm::logic::AtomicLabelFormula>("done");
  114. reachabilityRewardFormula = std::make_shared<storm::logic::ReachabilityRewardFormula>(apFormula);
  115. rewardFormula = std::make_shared<storm::logic::RewardOperatorFormula>(storm::logic::OptimalityType::Maximize, reachabilityRewardFormula);
  116. result = stateRewardModelChecker.check(*rewardFormula);
  117. #ifdef STORM_HAVE_CUDA
  118. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 7.333329499),
  119. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  120. #else
  121. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 7.33333151),
  122. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  123. #endif
  124. rewardFormula.reset();
  125. // -------------------------------- state and transition reward ------------------------
  126. std::shared_ptr<storm::models::sparse::Mdp<double>> stateAndTransitionRewardMdp = storm::parser::AutoParser::parseModel(STORM_CPP_BASE_PATH "/examples/mdp/two_dice/two_dice.tra", STORM_CPP_BASE_PATH "/examples/mdp/two_dice/two_dice.lab", STORM_CPP_BASE_PATH "/examples/mdp/two_dice/two_dice.flip.state.rew", STORM_CPP_BASE_PATH "/examples/mdp/two_dice/two_dice.flip.trans.rew")->as<storm::models::sparse::Mdp<double>>();
  127. storm::modelchecker::SparseMdpPrctlModelChecker<double> stateAndTransitionRewardModelChecker(*stateAndTransitionRewardMdp, std::unique_ptr<storm::utility::solver::MinMaxLinearEquationSolverFactory<double>>(new storm::utility::solver::TopologicalMinMaxLinearEquationSolverFactory<double>()));
  128. apFormula = std::make_shared<storm::logic::AtomicLabelFormula>("done");
  129. reachabilityRewardFormula = std::make_shared<storm::logic::ReachabilityRewardFormula>(apFormula);
  130. rewardFormula = std::make_shared<storm::logic::RewardOperatorFormula>(storm::logic::OptimalityType::Minimize, reachabilityRewardFormula);
  131. result = stateAndTransitionRewardModelChecker.check(*rewardFormula);
  132. #ifdef STORM_HAVE_CUDA
  133. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 14.666658998),
  134. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  135. #else
  136. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 14.6666581),
  137. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  138. #endif
  139. rewardFormula.reset();
  140. apFormula = std::make_shared<storm::logic::AtomicLabelFormula>("done");
  141. reachabilityRewardFormula = std::make_shared<storm::logic::ReachabilityRewardFormula>(apFormula);
  142. rewardFormula = std::make_shared<storm::logic::RewardOperatorFormula>(storm::logic::OptimalityType::Maximize, reachabilityRewardFormula);
  143. result = stateAndTransitionRewardModelChecker.check(*rewardFormula);
  144. #ifdef STORM_HAVE_CUDA
  145. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 14.666658998),
  146. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  147. #else
  148. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 14.666663),
  149. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  150. #endif
  151. rewardFormula.reset();
  152. }
  153. TEST(TopologicalValueIterationMdpPrctlModelCheckerTest, AsynchronousLeader) {
  154. std::shared_ptr<storm::models::sparse::Mdp<double>> mdp = storm::parser::AutoParser::parseModel(STORM_CPP_BASE_PATH "/examples/mdp/asynchronous_leader/leader4.tra", STORM_CPP_BASE_PATH "/examples/mdp/asynchronous_leader/leader4.lab", "", STORM_CPP_BASE_PATH "/examples/mdp/asynchronous_leader/leader4.trans.rew")->as<storm::models::sparse::Mdp<double>>();
  155. ASSERT_EQ(mdp->getNumberOfStates(), 3172ull);
  156. ASSERT_EQ(mdp->getNumberOfTransitions(), 7144ull);
  157. storm::modelchecker::SparseMdpPrctlModelChecker<double> mc(*mdp, std::unique_ptr<storm::utility::solver::MinMaxLinearEquationSolverFactory<double>>(new storm::utility::solver::TopologicalMinMaxLinearEquationSolverFactory<double>()));
  158. auto apFormula = std::make_shared<storm::logic::AtomicLabelFormula>("elected");
  159. auto eventuallyFormula = std::make_shared<storm::logic::EventuallyFormula>(apFormula);
  160. auto probabilityOperatorFormula = std::make_shared<storm::logic::ProbabilityOperatorFormula>(storm::logic::OptimalityType::Minimize, eventuallyFormula);
  161. std::unique_ptr<storm::modelchecker::CheckResult> result = mc.check(*probabilityOperatorFormula);
  162. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 1),
  163. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  164. probabilityOperatorFormula.reset();
  165. apFormula = std::make_shared<storm::logic::AtomicLabelFormula>("elected");
  166. eventuallyFormula = std::make_shared<storm::logic::EventuallyFormula>(apFormula);
  167. probabilityOperatorFormula = std::make_shared<storm::logic::ProbabilityOperatorFormula>(storm::logic::OptimalityType::Maximize, eventuallyFormula);
  168. result = mc.check(*probabilityOperatorFormula);
  169. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 1),
  170. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  171. probabilityOperatorFormula.reset();
  172. apFormula = std::make_shared<storm::logic::AtomicLabelFormula>("elected");
  173. auto boundedEventuallyFormula = std::make_shared<storm::logic::BoundedUntilFormula>(std::make_shared<storm::logic::BooleanLiteralFormula>(true), apFormula, 25);
  174. probabilityOperatorFormula = std::make_shared<storm::logic::ProbabilityOperatorFormula>(storm::logic::OptimalityType::Maximize, boundedEventuallyFormula);
  175. result = mc.check(*probabilityOperatorFormula);
  176. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 0.0625),
  177. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  178. probabilityOperatorFormula.reset();
  179. apFormula = std::make_shared<storm::logic::AtomicLabelFormula>("elected");
  180. boundedEventuallyFormula = std::make_shared<storm::logic::BoundedUntilFormula>(std::make_shared<storm::logic::BooleanLiteralFormula>(true), apFormula, 25);
  181. probabilityOperatorFormula = std::make_shared<storm::logic::ProbabilityOperatorFormula>(storm::logic::OptimalityType::Minimize, boundedEventuallyFormula);
  182. result = mc.check(*probabilityOperatorFormula);
  183. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 0.0625),
  184. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  185. probabilityOperatorFormula.reset();
  186. apFormula = std::make_shared<storm::logic::AtomicLabelFormula>("elected");
  187. auto reachabilityRewardFormula = std::make_shared<storm::logic::ReachabilityRewardFormula>(apFormula);
  188. auto rewardFormula = std::make_shared<storm::logic::RewardOperatorFormula>(storm::logic::OptimalityType::Minimize, reachabilityRewardFormula);
  189. result = mc.check(*rewardFormula);
  190. #ifdef STORM_HAVE_CUDA
  191. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 4.285689611),
  192. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  193. #else
  194. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 4.285701547),
  195. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  196. #endif
  197. probabilityOperatorFormula.reset();
  198. apFormula = std::make_shared<storm::logic::AtomicLabelFormula>("elected");
  199. reachabilityRewardFormula = std::make_shared<storm::logic::ReachabilityRewardFormula>(apFormula);
  200. rewardFormula = std::make_shared<storm::logic::RewardOperatorFormula>(storm::logic::OptimalityType::Maximize, reachabilityRewardFormula);
  201. result = mc.check(*rewardFormula);
  202. #ifdef STORM_HAVE_CUDA
  203. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 4.285689611),
  204. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  205. #else
  206. ASSERT_LT(std::abs(result->asExplicitQuantitativeCheckResult<double>()[0] - 4.285703591),
  207. storm::settings::topologicalValueIterationEquationSolverSettings().getPrecision());
  208. #endif
  209. probabilityOperatorFormula.reset();
  210. }