Skip to content

Commit f786f18

Browse files
committed
Simplify conditional in predicate
1 parent df2314b commit f786f18

File tree

2 files changed

+29
-0
lines changed

2 files changed

+29
-0
lines changed

sql/catalyst/src/main/scala/org/apache/spark/sql/catalyst/optimizer/Optimizer.scala

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -103,6 +103,7 @@ abstract class Optimizer(catalogManager: CatalogManager)
103103
RemoveDispensableExpressions,
104104
SimplifyBinaryComparison,
105105
ReplaceNullWithFalseInPredicate,
106+
SimplifyConditionalInPredicate,
106107
PruneFilters,
107108
SimplifyCasts,
108109
SimplifyCaseConversionExpressions,

sql/catalyst/src/main/scala/org/apache/spark/sql/catalyst/optimizer/expressions.scala

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,7 @@ import org.apache.spark.sql.catalyst.plans.logical._
3030
import org.apache.spark.sql.catalyst.rules._
3131
import org.apache.spark.sql.internal.SQLConf
3232
import org.apache.spark.sql.types._
33+
import org.apache.spark.util.Utils
3334

3435
/*
3536
* Optimization rules defined in this file should not affect the structure of the logical plan.
@@ -570,6 +571,33 @@ object PushFoldableIntoBranches extends Rule[LogicalPlan] with PredicateHelper {
570571
}
571572

572573

574+
object SimplifyConditionalInPredicate extends Rule[LogicalPlan] {
575+
def apply(plan: LogicalPlan): LogicalPlan = plan transform {
576+
case f @ Filter(cond, _) => f.copy(condition = simplifyConditional(cond))
577+
}
578+
579+
private def simplifyConditional(e: Expression): Expression = e match {
580+
case cw @ CaseWhen(branches, elseValue) if cw.dataType == BooleanType && branches.size == 1 &&
581+
elseValue.forall(_.semanticEquals(FalseLiteral)) =>
582+
val (whenVal, thenVal) = branches.head
583+
And(whenVal, thenVal)
584+
case i @ If(pred, trueVal, FalseLiteral) if i.dataType == BooleanType =>
585+
And(pred, trueVal)
586+
case e if e.dataType == BooleanType =>
587+
e
588+
case e =>
589+
val message = "Expected a Boolean type expression in simplifyConditional, " +
590+
s"but got the type `${e.dataType.catalogString}` in `${e.sql}`."
591+
if (Utils.isTesting) {
592+
throw new IllegalArgumentException(message)
593+
} else {
594+
logWarning(message)
595+
e
596+
}
597+
}
598+
}
599+
600+
573601
/**
574602
* Simplifies LIKE expressions that do not need full regular expressions to evaluate the condition.
575603
* For example, when the expression is just checking to see if a string starts with a given

0 commit comments

Comments
 (0)