#include "storm/solver/NativeMultiplier.h" #include "storm-config.h" #include "storm/environment/solver/MultiplierEnvironment.h" #include "storm/settings/SettingsManager.h" #include "storm/settings/modules/CoreSettings.h" #include "storm/storage/SparseMatrix.h" #include "storm/adapters/RationalNumberAdapter.h" #include "storm/adapters/RationalFunctionAdapter.h" #include "storm/adapters/IntelTbbAdapter.h" #include "storm/utility/macros.h" namespace storm { namespace solver { template NativeMultiplier::NativeMultiplier(storm::storage::SparseMatrix const& matrix) : Multiplier(matrix) { // Intentionally left empty. } template bool NativeMultiplier::parallelize(Environment const& env) const { #ifdef STORM_HAVE_INTELTBB return storm::settings::getModule().isUseIntelTbbSet(); #else return false; #endif } template void NativeMultiplier::multiply(Environment const& env, std::vector const& x, std::vector const* b, std::vector& result) const { std::vector* target = &result; if (&x == &result) { if (this->cachedVector) { this->cachedVector->resize(x.size()); } else { this->cachedVector = std::make_unique>(x.size()); } target = this->cachedVector.get(); } if (parallelize(env)) { multAddParallel(x, b, *target); } else { multAdd(x, b, *target); } if (&x == &result) { std::swap(result, *this->cachedVector); } } template void NativeMultiplier::multiplyGaussSeidel(Environment const& env, std::vector& x, std::vector const* b, bool backwards) const { if (backwards) { this->matrix.multiplyWithVectorBackward(x, x, b); } else { this->matrix.multiplyWithVectorForward(x, x, b); } } template void NativeMultiplier::multiplyAndReduce(Environment const& env, OptimizationDirection const& dir, std::vector const& rowGroupIndices, std::vector const& x, std::vector const* b, std::vector& result, std::vector* choices) const { std::vector* target = &result; if (&x == &result) { if (this->cachedVector) { this->cachedVector->resize(x.size()); } else { this->cachedVector = std::make_unique>(x.size()); } target = this->cachedVector.get(); } if (parallelize(env)) { multAddReduceParallel(dir, rowGroupIndices, x, b, *target, choices); } else { multAddReduce(dir, rowGroupIndices, x, b, *target, choices); } if (&x == &result) { std::swap(result, *this->cachedVector); } } template void NativeMultiplier::multiplyAndReduceGaussSeidel(Environment const& env, OptimizationDirection const& dir, std::vector const& rowGroupIndices, std::vector& x, std::vector const* b, std::vector* choices, bool backwards) const { if (backwards) { this->matrix.multiplyAndReduceBackward(dir, rowGroupIndices, x, b, x, choices); } else { this->matrix.multiplyAndReduceForward(dir, rowGroupIndices, x, b, x, choices); } } template void NativeMultiplier::multiplyRow(uint64_t const& rowIndex, std::vector const& x, ValueType& value) const { for (auto const& entry : this->matrix.getRow(rowIndex)) { value += entry.getValue() * x[entry.getColumn()]; } } template void NativeMultiplier::multiplyRow2(uint64_t const& rowIndex, std::vector const& x1, ValueType& val1, std::vector const& x2, ValueType& val2) const { for (auto const& entry : this->matrix.getRow(rowIndex)) { val1 += entry.getValue() * x1[entry.getColumn()]; val2 += entry.getValue() * x2[entry.getColumn()]; } } template void NativeMultiplier::multAdd(std::vector const& x, std::vector const* b, std::vector& result) const { this->matrix.multiplyWithVector(x, result, b); } template void NativeMultiplier::multAddReduce(storm::solver::OptimizationDirection const& dir, std::vector const& rowGroupIndices, std::vector const& x, std::vector const* b, std::vector& result, std::vector* choices) const { this->matrix.multiplyAndReduce(dir, rowGroupIndices, x, b, result, choices); } template void NativeMultiplier::multAddParallel(std::vector const& x, std::vector const* b, std::vector& result) const { #ifdef STORM_HAVE_INTELTBB this->matrix.multiplyWithVectorParallel(x, result, b); #else STORM_LOG_WARN("Storm was built without support for Intel TBB, defaulting to sequential version."); multAdd(x, b, result); #endif } template void NativeMultiplier::multAddReduceParallel(storm::solver::OptimizationDirection const& dir, std::vector const& rowGroupIndices, std::vector const& x, std::vector const* b, std::vector& result, std::vector* choices) const { #ifdef STORM_HAVE_INTELTBB this->matrix.multiplyAndReduceParallel(dir, rowGroupIndices, x, b, result, choices); #else STORM_LOG_WARN("Storm was built without support for Intel TBB, defaulting to sequential version."); multAddReduce(dir, rowGroupIndices, x, b, result, choices); #endif } template class NativeMultiplier; #ifdef STORM_HAVE_CARL template class NativeMultiplier; template class NativeMultiplier; #endif } }