Storm
A Modern Probabilistic Model Checker
Loading...
Searching...
No Matches
UnaryNumericalFunctionExpression.cpp
Go to the documentation of this file.
1#include <cmath>
2
3#include "ExpressionVisitor.h"
4
14
15namespace storm {
16namespace expressions {
18 std::shared_ptr<BaseExpression const> const& operand, OperatorType operatorType)
19 : UnaryExpression(manager, type, operand), operatorType(operatorType) {
20 // Intentionally left empty.
21}
22
26
48
49int_fast64_t UnaryNumericalFunctionExpression::evaluateAsInt(Valuation const* valuation) const {
50 STORM_LOG_THROW(this->hasIntegerType(), storm::exceptions::InvalidTypeException, "Unable to evaluate expression as integer.");
51
52 if (this->getOperatorType() == OperatorType::Minus) {
53 STORM_LOG_THROW(this->getOperand()->hasIntegerType(), storm::exceptions::InvalidTypeException, "Unable to evaluate expression as integer.");
54 int_fast64_t result = this->getOperand()->evaluateAsInt(valuation);
55 return -result;
56 } else {
57 // TODO: this should evaluate the operand as a rational.
58 double result = this->getOperand()->evaluateAsDouble(valuation);
59 switch (this->getOperatorType()) {
61 return static_cast<int_fast64_t>(std::floor(result));
62 break;
64 return static_cast<int_fast64_t>(std::ceil(result));
65 break;
66 default:
67 STORM_LOG_ASSERT(false, "All other operator types should have been handled before.");
68 return 0; // Warning suppression.
69 }
70 }
71}
72
74 STORM_LOG_THROW(this->hasNumericalType(), storm::exceptions::InvalidTypeException, "Unable to evaluate expression as double.");
75
76 double result = this->getOperand()->evaluateAsDouble(valuation);
77 switch (this->getOperatorType()) {
79 result = -result;
80 break;
82 result = std::floor(result);
83 break;
85 result = std::ceil(result);
86 break;
88 result = std::cos(result);
89 break;
91 result = std::sin(result);
92 break;
93 }
94 return result;
95}
96
97std::shared_ptr<BaseExpression const> UnaryNumericalFunctionExpression::simplify() const {
98 std::shared_ptr<BaseExpression const> operandSimplified = this->getOperand()->simplify();
99
100 if (operandSimplified->isLiteral()) {
101 if (operandSimplified->hasIntegerType()) {
102 int_fast64_t intValue = operandSimplified->evaluateAsInt();
103 storm::RationalNumber rationalValue;
104 bool useInteger = true;
105 switch (this->getOperatorType()) {
107 intValue = -intValue;
108 break;
109 // Nothing to be done for the other cases:
112 break;
114 useInteger = false;
115 rationalValue = storm::utility::cos(storm::utility::convertNumber<storm::RationalNumber>(intValue));
116 break;
118 useInteger = false;
119 rationalValue = storm::utility::sin(storm::utility::convertNumber<storm::RationalNumber>(intValue));
120 break;
121 }
122 if (useInteger) {
123 return std::shared_ptr<BaseExpression>(new IntegerLiteralExpression(this->getManager(), intValue));
124 } else {
125 return std::shared_ptr<BaseExpression>(new RationalLiteralExpression(this->getManager(), rationalValue));
126 }
127 } else if (operandSimplified->hasRationalType()) {
128 storm::RationalNumber value = operandSimplified->evaluateAsRational();
129 bool convertToInteger = false;
130 switch (this->getOperatorType()) {
132 value = -value;
133 break;
135 value = storm::utility::floor(value);
136 convertToInteger = true;
137 break;
139 value = storm::utility::ceil(value);
140 convertToInteger = true;
141 break;
143 value = storm::utility::cos(value);
144 break;
146 value = storm::utility::sin(value);
147 break;
148 }
149 if (convertToInteger) {
150 return std::shared_ptr<BaseExpression>(new IntegerLiteralExpression(this->getManager(), storm::utility::convertNumber<int64_t>(value)));
151 } else {
152 return std::shared_ptr<BaseExpression>(new RationalLiteralExpression(this->getManager(), value));
153 }
154 }
155 }
156
157 if (operandSimplified.get() == this->getOperand().get()) {
158 return this->shared_from_this();
159 } else {
160 return std::shared_ptr<BaseExpression>(
161 new UnaryNumericalFunctionExpression(this->getManager(), this->getType(), operandSimplified, this->getOperatorType()));
162 }
163}
164
165boost::any UnaryNumericalFunctionExpression::accept(ExpressionVisitor& visitor, boost::any const& data) const {
166 return visitor.visit(*this, data);
167}
168
172
173void UnaryNumericalFunctionExpression::printToStream(std::ostream& stream) const {
174 switch (this->getOperatorType()) {
176 stream << "-(";
177 break;
179 stream << "floor(";
180 break;
182 stream << "ceil(";
183 break;
185 stream << "cos(";
186 break;
188 stream << "sin(";
189 break;
190 }
191 stream << *this->getOperand() << ")";
192}
193} // namespace expressions
194} // namespace storm
ExpressionManager const & getManager() const
Retrieves the manager responsible for this expression.
bool hasIntegerType() const
Retrieves whether the expression has an integer type.
bool hasNumericalType() const
Retrieves whether the expression has a numerical type, i.e., integer or double.
Type const & getType() const
Retrieves the type of the expression.
This class is responsible for managing a set of typed variables and all expressions using these varia...
virtual boost::any visit(IfThenElseExpression const &expression, boost::any const &data)=0
std::shared_ptr< BaseExpression const > const & getOperand() const
Retrieves the operand of the unary expression.
OperatorType
An enum type specifying the different functions applicable.
virtual int_fast64_t evaluateAsInt(Valuation const *valuation=nullptr) const override
Evaluates the expression under the valuation of unknowns (variables and constants) given by the valua...
virtual void printToStream(std::ostream &stream) const override
Prints the expression to the given stream.
OperatorType getOperatorType() const
Retrieves the operator associated with this expression.
virtual storm::expressions::OperatorType getOperator() const override
Retrieves the operator of a function application.
virtual std::shared_ptr< BaseExpression const > simplify() const override
Simplifies the expression according to some simple rules.
virtual boost::any accept(ExpressionVisitor &visitor, boost::any const &data) const override
Accepts the given visitor by calling its visit method.
UnaryNumericalFunctionExpression(ExpressionManager const &manager, Type const &type, std::shared_ptr< BaseExpression const > const &operand, OperatorType operatorType)
Creates a unary numerical function expression with the given return type, operand and operator.
virtual double evaluateAsDouble(Valuation const *valuation=nullptr) const override
Evaluates the expression under the valuation of unknowns (variables and constants) given by the valua...
The base class of all valuations of variables.
Definition Valuation.h:16
#define STORM_LOG_ASSERT(cond, message)
Definition macros.h:11
#define STORM_LOG_THROW(cond, exception, message)
Definition macros.h:30
ValueType sin(ValueType const &number)
ValueType floor(ValueType const &number)
ValueType ceil(ValueType const &number)
ValueType cos(ValueType const &number)
LabParser.cpp.
Definition cli.cpp:18