Derives the bounds of the given boolean expression
(&self, predicate: &Expr)
| 66 | impl PredicateBoundsEvaluator<'_> { |
| 67 | /// Derives the bounds of the given boolean expression |
| 68 | fn evaluate_bounds(&self, predicate: &Expr) -> Result<NullableInterval> { |
| 69 | Ok(match predicate { |
| 70 | Expr::Literal(scalar, _) => { |
| 71 | // Interpret literals as boolean, coercing if necessary |
| 72 | match scalar { |
| 73 | ScalarValue::Null => NullableInterval::UNKNOWN, |
| 74 | ScalarValue::Boolean(b) => match b { |
| 75 | Some(true) => NullableInterval::TRUE, |
| 76 | Some(false) => NullableInterval::FALSE, |
| 77 | None => NullableInterval::UNKNOWN, |
| 78 | }, |
| 79 | _ => { |
| 80 | let b = Expr::Literal(scalar.cast_to(&DataType::Boolean)?, None); |
| 81 | self.evaluate_bounds(&b)? |
| 82 | } |
| 83 | } |
| 84 | } |
| 85 | Expr::IsNull(e) => { |
| 86 | // If `e` is not nullable, then `e IS NULL` is provably false |
| 87 | if !e.nullable(self.input_schema)? { |
| 88 | NullableInterval::FALSE |
| 89 | } else { |
| 90 | match e.get_type(self.input_schema)? { |
| 91 | // If `e` is a boolean expression, check if `e` is provably 'unknown'. |
| 92 | DataType::Boolean => self.evaluate_bounds(e)?.is_unknown()?, |
| 93 | // If `e` is not a boolean expression, check if `e` is provably null |
| 94 | _ => self.is_null(e), |
| 95 | } |
| 96 | } |
| 97 | } |
| 98 | Expr::IsNotNull(e) => { |
| 99 | // If `e` is not nullable, then `e IS NOT NULL` is provably true |
| 100 | if !e.nullable(self.input_schema)? { |
| 101 | NullableInterval::TRUE |
| 102 | } else { |
| 103 | match e.get_type(self.input_schema)? { |
| 104 | // If `e` is a boolean expression, try to evaluate it and test for not unknown |
| 105 | DataType::Boolean => { |
| 106 | self.evaluate_bounds(e)?.is_unknown()?.not()? |
| 107 | } |
| 108 | // If `e` is not a boolean expression, check if `e` is provably null |
| 109 | _ => self.is_null(e).not()?, |
| 110 | } |
| 111 | } |
| 112 | } |
| 113 | Expr::IsTrue(e) => self.evaluate_bounds(e)?.is_true()?, |
| 114 | Expr::IsNotTrue(e) => self.evaluate_bounds(e)?.is_true()?.not()?, |
| 115 | Expr::IsFalse(e) => self.evaluate_bounds(e)?.is_false()?, |
| 116 | Expr::IsNotFalse(e) => self.evaluate_bounds(e)?.is_false()?.not()?, |
| 117 | Expr::IsUnknown(e) => self.evaluate_bounds(e)?.is_unknown()?, |
| 118 | Expr::IsNotUnknown(e) => self.evaluate_bounds(e)?.is_unknown()?.not()?, |
| 119 | Expr::Not(e) => self.evaluate_bounds(e)?.not()?, |
| 120 | Expr::BinaryExpr(BinaryExpr { |
| 121 | left, |
| 122 | op: Operator::And, |
| 123 | right, |
| 124 | }) => NullableInterval::and( |
| 125 | &self.evaluate_bounds(left)?, |
no test coverage detected