Browse Source

added new uniform heuristic and changed probdiff to be the sum instead of product

Former-commit-id: 6fcb9ad80b
main
dehnert 9 years ago
parent
commit
313edf44e1
  1. 3
      src/modelchecker/exploration/Bounds.cpp
  2. 12
      src/modelchecker/exploration/ExplorationInformation.cpp
  3. 4
      src/modelchecker/exploration/ExplorationInformation.h
  4. 25
      src/modelchecker/exploration/SparseMdpExplorationModelChecker.cpp
  5. 10
      src/settings/modules/ExplorationSettings.cpp
  6. 2
      src/settings/modules/ExplorationSettings.h

3
src/modelchecker/exploration/Bounds.cpp

@ -10,10 +10,8 @@ namespace storm {
std::pair<ValueType, ValueType> Bounds<StateType, ValueType>::getBoundsForState(StateType const& state, ExplorationInformation<StateType, ValueType> const& explorationInformation) const { std::pair<ValueType, ValueType> Bounds<StateType, ValueType>::getBoundsForState(StateType const& state, ExplorationInformation<StateType, ValueType> const& explorationInformation) const {
ActionType index = explorationInformation.getRowGroup(state); ActionType index = explorationInformation.getRowGroup(state);
if (index == explorationInformation.getUnexploredMarker()) { if (index == explorationInformation.getUnexploredMarker()) {
std::cout << "state " << state << " is unexplored! retuning zero/one" << std::endl;
return std::make_pair(storm::utility::zero<ValueType>(), storm::utility::one<ValueType>()); return std::make_pair(storm::utility::zero<ValueType>(), storm::utility::one<ValueType>());
} else { } else {
std::cout << "accessing at index " << index << " out of " << boundsPerState.size() << std::endl;
return boundsPerState[index]; return boundsPerState[index];
} }
} }
@ -116,7 +114,6 @@ namespace storm {
template<typename StateType, typename ValueType> template<typename StateType, typename ValueType>
void Bounds<StateType, ValueType>::setBoundsForState(StateType const& state, ExplorationInformation<StateType, ValueType> const& explorationInformation, std::pair<ValueType, ValueType> const& values) { void Bounds<StateType, ValueType>::setBoundsForState(StateType const& state, ExplorationInformation<StateType, ValueType> const& explorationInformation, std::pair<ValueType, ValueType> const& values) {
StateType const& rowGroup = explorationInformation.getRowGroup(state); StateType const& rowGroup = explorationInformation.getRowGroup(state);
std::cout << "setting " << values.first << ", " << values.second << " for state " << state << std::endl;
setBoundsForRowGroup(rowGroup, values); setBoundsForRowGroup(rowGroup, values);
} }

12
src/modelchecker/exploration/ExplorationInformation.cpp

@ -10,7 +10,7 @@ namespace storm {
namespace exploration_detail { namespace exploration_detail {
template<typename StateType, typename ValueType> template<typename StateType, typename ValueType>
ExplorationInformation<StateType, ValueType>::ExplorationInformation(storm::OptimizationDirection const& direction, ActionType const& unexploredMarker) : unexploredMarker(unexploredMarker), optimizationDirection(direction), localPrecomputation(false), numberOfExplorationStepsUntilPrecomputation(100000), numberOfSampledPathsUntilPrecomputation(), nextStateHeuristic(storm::settings::modules::ExplorationSettings::NextStateHeuristic::DifferenceWeightedProbability) {
ExplorationInformation<StateType, ValueType>::ExplorationInformation(storm::OptimizationDirection const& direction, ActionType const& unexploredMarker) : unexploredMarker(unexploredMarker), optimizationDirection(direction), localPrecomputation(false), numberOfExplorationStepsUntilPrecomputation(100000), numberOfSampledPathsUntilPrecomputation(), nextStateHeuristic(storm::settings::modules::ExplorationSettings::NextStateHeuristic::DifferenceProbabilitySum) {
storm::settings::modules::ExplorationSettings const& settings = storm::settings::explorationSettings(); storm::settings::modules::ExplorationSettings const& settings = storm::settings::explorationSettings();
localPrecomputation = settings.isLocalPrecomputationSet(); localPrecomputation = settings.isLocalPrecomputationSet();
@ -20,7 +20,6 @@ namespace storm {
} }
nextStateHeuristic = settings.getNextStateHeuristic(); nextStateHeuristic = settings.getNextStateHeuristic();
STORM_LOG_ASSERT(useDifferenceWeightedProbabilityHeuristic() || useProbabilityHeuristic(), "Illegal next-state heuristic.");
} }
template<typename StateType, typename ValueType> template<typename StateType, typename ValueType>
@ -198,8 +197,8 @@ namespace storm {
} }
template<typename StateType, typename ValueType> template<typename StateType, typename ValueType>
bool ExplorationInformation<StateType, ValueType>::useDifferenceWeightedProbabilityHeuristic() const {
return nextStateHeuristic == storm::settings::modules::ExplorationSettings::NextStateHeuristic::DifferenceWeightedProbability;
bool ExplorationInformation<StateType, ValueType>::useDifferenceProbabilitySumHeuristic() const {
return nextStateHeuristic == storm::settings::modules::ExplorationSettings::NextStateHeuristic::DifferenceProbabilitySum;
} }
template<typename StateType, typename ValueType> template<typename StateType, typename ValueType>
@ -207,6 +206,11 @@ namespace storm {
return nextStateHeuristic == storm::settings::modules::ExplorationSettings::NextStateHeuristic::Probability; return nextStateHeuristic == storm::settings::modules::ExplorationSettings::NextStateHeuristic::Probability;
} }
template<typename StateType, typename ValueType>
bool ExplorationInformation<StateType, ValueType>::useUniformHeuristic() const {
return nextStateHeuristic == storm::settings::modules::ExplorationSettings::NextStateHeuristic::Uniform;
}
template<typename StateType, typename ValueType> template<typename StateType, typename ValueType>
storm::OptimizationDirection const& ExplorationInformation<StateType, ValueType>::getOptimizationDirection() const { storm::OptimizationDirection const& ExplorationInformation<StateType, ValueType>::getOptimizationDirection() const {
return optimizationDirection; return optimizationDirection;

4
src/modelchecker/exploration/ExplorationInformation.h

@ -94,10 +94,12 @@ namespace storm {
storm::settings::modules::ExplorationSettings::NextStateHeuristic const& getNextStateHeuristic() const; storm::settings::modules::ExplorationSettings::NextStateHeuristic const& getNextStateHeuristic() const;
bool useDifferenceWeightedProbabilityHeuristic() const;
bool useDifferenceProbabilitySumHeuristic() const;
bool useProbabilityHeuristic() const; bool useProbabilityHeuristic() const;
bool useUniformHeuristic() const;
storm::OptimizationDirection const& getOptimizationDirection() const; storm::OptimizationDirection const& getOptimizationDirection() const;
void setOptimizationDirection(storm::OptimizationDirection const& direction); void setOptimizationDirection(storm::OptimizationDirection const& direction);

25
src/modelchecker/exploration/SparseMdpExplorationModelChecker.cpp

@ -237,7 +237,7 @@ namespace storm {
for (auto const& choice : behavior) { for (auto const& choice : behavior) {
for (auto const& entry : choice) { for (auto const& entry : choice) {
explorationInformation.getRowOfMatrix(startAction + localAction).emplace_back(entry.first, entry.second); explorationInformation.getRowOfMatrix(startAction + localAction).emplace_back(entry.first, entry.second);
std::cout << "adding " << (startAction + localAction) << "x" << entry.first << " -> " << entry.second << std::endl;
STORM_LOG_TRACE("Found transition " << currentStateId << "-[" << (startAction + localAction) << ", " << entry.second << "]-> " << entry.first << ".");
} }
std::pair<ValueType, ValueType> actionBounds = computeBoundsOfAction(startAction + localAction, explorationInformation, bounds); std::pair<ValueType, ValueType> actionBounds = computeBoundsOfAction(startAction + localAction, explorationInformation, bounds);
@ -328,14 +328,14 @@ namespace storm {
return row.front().getColumn(); return row.front().getColumn();
} }
std::vector<ValueType> probabilities(row.size());
// Depending on the selected next-state heuristic, we give the states other likelihoods of getting chosen. // Depending on the selected next-state heuristic, we give the states other likelihoods of getting chosen.
if (explorationInformation.useDifferenceWeightedProbabilityHeuristic()) {
if (explorationInformation.useDifferenceProbabilitySumHeuristic() || explorationInformation.useProbabilityHeuristic()) {
std::vector<ValueType> probabilities(row.size());
if (explorationInformation.useDifferenceProbabilitySumHeuristic()) {
std::transform(row.begin(), row.end(), probabilities.begin(), std::transform(row.begin(), row.end(), probabilities.begin(),
[&bounds, &explorationInformation] (storm::storage::MatrixEntry<StateType, ValueType> const& entry) { [&bounds, &explorationInformation] (storm::storage::MatrixEntry<StateType, ValueType> const& entry) {
std::cout << entry.getColumn() << " with diff " << bounds.getDifferenceOfStateBounds(entry.getColumn(), explorationInformation) << std::endl;
return entry.getValue() * bounds.getDifferenceOfStateBounds(entry.getColumn(), explorationInformation);
return entry.getValue() + bounds.getDifferenceOfStateBounds(entry.getColumn(), explorationInformation);
}); });
} else if (explorationInformation.useProbabilityHeuristic()) { } else if (explorationInformation.useProbabilityHeuristic()) {
std::transform(row.begin(), row.end(), probabilities.begin(), std::transform(row.begin(), row.end(), probabilities.begin(),
@ -346,8 +346,11 @@ namespace storm {
// Now sample according to the probabilities. // Now sample according to the probabilities.
std::discrete_distribution<StateType> distribution(probabilities.begin(), probabilities.end()); std::discrete_distribution<StateType> distribution(probabilities.begin(), probabilities.end());
StateType offset = distribution(randomGenerator);
return row[offset].getColumn();
return row[distribution(randomGenerator)].getColumn();
} else if (explorationInformation.useUniformHeuristic()) {
std::uniform_int_distribution<ActionType> distribution(0, row.size() - 1);
return row[distribution(randomGenerator)].getColumn();
}
} }
template<typename ValueType> template<typename ValueType>
@ -390,10 +393,8 @@ namespace storm {
storm::storage::BitVector targetStates(sink + 1); storm::storage::BitVector targetStates(sink + 1);
for (StateType index = 0; index < relevantStates.size(); ++index) { for (StateType index = 0; index < relevantStates.size(); ++index) {
relevantStateToNewRowGroupMapping.emplace(relevantStates[index], index); relevantStateToNewRowGroupMapping.emplace(relevantStates[index], index);
std::cout << "lower bound for state " << relevantStates[index] << " is " << bounds.getLowerBoundForState(relevantStates[index], explorationInformation) << std::endl;
if (storm::utility::isOne(bounds.getLowerBoundForState(relevantStates[index], explorationInformation))) { if (storm::utility::isOne(bounds.getLowerBoundForState(relevantStates[index], explorationInformation))) {
targetStates.set(index); targetStates.set(index);
std::cout << relevantStates[index] << " was identified as a target state" << std::endl;
} }
} }
@ -409,11 +410,9 @@ namespace storm {
if (it != relevantStateToNewRowGroupMapping.end()) { if (it != relevantStateToNewRowGroupMapping.end()) {
// If the entry is a relevant state, we copy it over (and compensate for the offset change). // If the entry is a relevant state, we copy it over (and compensate for the offset change).
builder.addNextValue(currentRow, it->second, entry.getValue()); builder.addNextValue(currentRow, it->second, entry.getValue());
std::cout << state << " to " << entry.getColumn() << " with prob " << entry.getValue() << std::endl;
} else { } else {
// If the entry is an unexpanded state, we gather the probability to later redirect it to an unexpanded sink. // If the entry is an unexpanded state, we gather the probability to later redirect it to an unexpanded sink.
unexpandedProbability += entry.getValue(); unexpandedProbability += entry.getValue();
std::cout << state << " has unexpanded prob " << unexpandedProbability << " to succ " << entry.getColumn() << std::endl;
} }
} }
if (unexpandedProbability != storm::utility::zero<ValueType>()) { if (unexpandedProbability != storm::utility::zero<ValueType>()) {
@ -473,13 +472,9 @@ namespace storm {
statesWithProbability1 = storm::utility::graph::performProb1A(relevantStatesMatrix, relevantStatesMatrix.getRowGroupIndices(), transposedMatrix, allStates, targetStates); statesWithProbability1 = storm::utility::graph::performProb1A(relevantStatesMatrix, relevantStatesMatrix.getRowGroupIndices(), transposedMatrix, allStates, targetStates);
} }
std::cout << statesWithProbability0 << std::endl;
std::cout << statesWithProbability1 << std::endl;
// Set the bounds of the identified states. // Set the bounds of the identified states.
for (auto state : statesWithProbability0) { for (auto state : statesWithProbability0) {
StateType originalState = relevantStates[state]; StateType originalState = relevantStates[state];
std::cout << "determined " << originalState << " as a prob0 state" << std::endl;
bounds.setUpperBoundForState(originalState, explorationInformation, storm::utility::zero<ValueType>()); bounds.setUpperBoundForState(originalState, explorationInformation, storm::utility::zero<ValueType>());
explorationInformation.addTerminalState(originalState); explorationInformation.addTerminalState(originalState);
} }

10
src/settings/modules/ExplorationSettings.cpp

@ -22,8 +22,8 @@ namespace storm {
this->addOption(storm::settings::OptionBuilder(moduleName, numberOfExplorationStepsUntilPrecomputationOptionName, true, "Sets the number of exploration steps to perform until a precomputation is triggered.").addArgument(storm::settings::ArgumentBuilder::createUnsignedIntegerArgument("count", "The number of exploration steps to perform.").setDefaultValueUnsignedInteger(100000).build()).build()); this->addOption(storm::settings::OptionBuilder(moduleName, numberOfExplorationStepsUntilPrecomputationOptionName, true, "Sets the number of exploration steps to perform until a precomputation is triggered.").addArgument(storm::settings::ArgumentBuilder::createUnsignedIntegerArgument("count", "The number of exploration steps to perform.").setDefaultValueUnsignedInteger(100000).build()).build());
this->addOption(storm::settings::OptionBuilder(moduleName, numberOfSampledPathsUntilPrecomputationOptionName, true, "If set, a precomputation is perfomed periodically after the given number of paths has been sampled.").addArgument(storm::settings::ArgumentBuilder::createUnsignedIntegerArgument("count", "The number of paths to sample until a precomputation is triggered.").setDefaultValueUnsignedInteger(100000).build()).build()); this->addOption(storm::settings::OptionBuilder(moduleName, numberOfSampledPathsUntilPrecomputationOptionName, true, "If set, a precomputation is perfomed periodically after the given number of paths has been sampled.").addArgument(storm::settings::ArgumentBuilder::createUnsignedIntegerArgument("count", "The number of paths to sample until a precomputation is triggered.").setDefaultValueUnsignedInteger(100000).build()).build());
std::vector<std::string> nextStateHeuristics = { "probdiff", "prob" };
this->addOption(storm::settings::OptionBuilder(moduleName, nextStateHeuristicOptionName, true, "Sets the next-state heuristic to use. Available are: { probdiff, prob } where 'prob' samples according to the probabilities in the system and 'probdiff' weights the probabilities with the differences between the current bounds.").addArgument(storm::settings::ArgumentBuilder::createStringArgument("name", "The name of the heuristic to use.").addValidationFunctionString(storm::settings::ArgumentValidators::stringInListValidator(nextStateHeuristics)).setDefaultValueString("probdiff").build()).build());
std::vector<std::string> nextStateHeuristics = { "probdiffs", "prob", "unif" };
this->addOption(storm::settings::OptionBuilder(moduleName, nextStateHeuristicOptionName, true, "Sets the next-state heuristic to use. Available are: { probdiffs, prob, unif } where 'prob' samples according to the probabilities in the system, 'probdiffs' takes into account probabilities and the differences between the current bounds and 'unif' samples uniformly.").addArgument(storm::settings::ArgumentBuilder::createStringArgument("name", "The name of the heuristic to use.").addValidationFunctionString(storm::settings::ArgumentValidators::stringInListValidator(nextStateHeuristics)).setDefaultValueString("probdiffs").build()).build());
} }
bool ExplorationSettings::isLocalPrecomputationSet() const { bool ExplorationSettings::isLocalPrecomputationSet() const {
@ -64,10 +64,12 @@ namespace storm {
ExplorationSettings::NextStateHeuristic ExplorationSettings::getNextStateHeuristic() const { ExplorationSettings::NextStateHeuristic ExplorationSettings::getNextStateHeuristic() const {
std::string nextStateHeuristicAsString = this->getOption(nextStateHeuristicOptionName).getArgumentByName("name").getValueAsString(); std::string nextStateHeuristicAsString = this->getOption(nextStateHeuristicOptionName).getArgumentByName("name").getValueAsString();
if (nextStateHeuristicAsString == "probdiff") {
return ExplorationSettings::NextStateHeuristic::DifferenceWeightedProbability;
if (nextStateHeuristicAsString == "probdiffs") {
return ExplorationSettings::NextStateHeuristic::DifferenceProbabilitySum;
} else if (nextStateHeuristicAsString == "prob") { } else if (nextStateHeuristicAsString == "prob") {
return ExplorationSettings::NextStateHeuristic::Probability; return ExplorationSettings::NextStateHeuristic::Probability;
} else if (nextStateHeuristicAsString == "unif") {
return ExplorationSettings::NextStateHeuristic::Uniform;
} }
STORM_LOG_THROW(false, storm::exceptions::IllegalArgumentValueException, "Unknown next-state heuristic '" << nextStateHeuristicAsString << "'."); STORM_LOG_THROW(false, storm::exceptions::IllegalArgumentValueException, "Unknown next-state heuristic '" << nextStateHeuristicAsString << "'.");
} }

2
src/settings/modules/ExplorationSettings.h

@ -16,7 +16,7 @@ namespace storm {
enum class PrecomputationType { Local, Global }; enum class PrecomputationType { Local, Global };
// The available heuristics to choose the next state. // The available heuristics to choose the next state.
enum class NextStateHeuristic { DifferenceWeightedProbability, Probability };
enum class NextStateHeuristic { DifferenceProbabilitySum, Probability, Uniform };
/*! /*!
* Creates a new set of exploration settings that is managed by the given manager. * Creates a new set of exploration settings that is managed by the given manager.

Loading…
Cancel
Save