mirror of
https://github.com/UpsilonNumworks/Upsilon.git
synced 2026-01-19 00:37:25 +01:00
[poincare] Randint::shallowReduce: replace by undef if the argument was
defined but not the randint approximation. This fixes tests: randint(1,inf) --> NAN, randint([[1,2]],2) --> NAN
This commit is contained in:
committed by
LeaNumworks
parent
6916b6e06f
commit
ab420b871c
@@ -6,6 +6,7 @@
|
||||
namespace Poincare {
|
||||
|
||||
class RandintNode /*final*/ : public ExpressionNode {
|
||||
friend class Randint;
|
||||
public:
|
||||
|
||||
// TreeNode
|
||||
@@ -33,7 +34,7 @@ private:
|
||||
Evaluation<double> approximate(DoublePrecision p, Context * context, Preferences::ComplexFormat complexFormat, Preferences::AngleUnit angleUnit) const override {
|
||||
return templateApproximate<double>(context, complexFormat, angleUnit);
|
||||
}
|
||||
template <typename T> Evaluation<T> templateApproximate(Context * context, Preferences::ComplexFormat complexFormat, Preferences::AngleUnit angleUnit) const;
|
||||
template <typename T> Evaluation<T> templateApproximate(Context * context, Preferences::ComplexFormat complexFormat, Preferences::AngleUnit angleUnit, bool * inputIsUndefined = nullptr) const;
|
||||
// Simplification
|
||||
Expression shallowReduce(ReductionContext reductionContext) override;
|
||||
LayoutShape leftLayoutShape() const override { return LayoutShape::MoreLetters; };
|
||||
|
||||
@@ -28,9 +28,12 @@ int RandintNode::serialize(char * buffer, int bufferSize, Preferences::PrintFloa
|
||||
return SerializationHelper::Prefix(this, buffer, bufferSize, floatDisplayMode, numberOfSignificantDigits, Randint::s_functionHelper.name());
|
||||
}
|
||||
|
||||
template <typename T> Evaluation<T> RandintNode::templateApproximate(Context * context, Preferences::ComplexFormat complexFormat, Preferences::AngleUnit angleUnit) const {
|
||||
template <typename T> Evaluation<T> RandintNode::templateApproximate(Context * context, Preferences::ComplexFormat complexFormat, Preferences::AngleUnit angleUnit, bool * inputIsUndefined) const {
|
||||
Evaluation<T> aInput = childAtIndex(0)->approximate(T(), context, complexFormat, angleUnit);
|
||||
Evaluation<T> bInput = childAtIndex(1)->approximate(T(), context, complexFormat, angleUnit);
|
||||
if (inputIsUndefined) {
|
||||
*inputIsUndefined = aInput.isUndefined() || bInput.isUndefined();
|
||||
}
|
||||
T a = aInput.toScalar();
|
||||
T b = bInput.toScalar();
|
||||
if (std::isnan(a) || std::isnan(b) || a != std::round(a) || b != std::round(b) || a > b || std::isinf(a) || std::isinf(b)) {
|
||||
@@ -49,9 +52,10 @@ Expression Randint::shallowReduce(ExpressionNode::ReductionContext reductionCont
|
||||
if (e.isUndefined()) {
|
||||
return e;
|
||||
}
|
||||
double eval = approximateToScalar<double>(reductionContext.context() , reductionContext.complexFormat() , reductionContext.angleUnit() );
|
||||
if (std::isnan(eval)) {
|
||||
/* The result might be NAN because we are reducing a function's expression
|
||||
bool inputIsUndefined = false;
|
||||
double eval = static_cast<RandintNode *>(node())->templateApproximate<double>(reductionContext.context(), reductionContext.complexFormat(), reductionContext.angleUnit(), &inputIsUndefined).toScalar();
|
||||
if (inputIsUndefined) {
|
||||
/* The input might be NAN because we are reducing a function's expression
|
||||
* which depends on x. We thus do not want to replace too early with
|
||||
* undefined. */
|
||||
return *this;
|
||||
|
||||
Reference in New Issue
Block a user