Skip to content

Commit

Permalink
[SPARK-13869][SQL] Remove redundant conditions while combining filters
Browse files Browse the repository at this point in the history
## What changes were proposed in this pull request?

**[I'll link it to the JIRA once ASF JIRA is back online]**

This PR modifies the existing `CombineFilters` rule to remove redundant conditions while combining individual filter predicates. For instance, queries of the form `table.where('a === 1 && 'b === 1).where('a === 1 && 'c === 1)` will now be optimized to ` table.where('a === 1 && 'b === 1 && 'c === 1)` (instead of ` table.where('a === 1 && 'a === 1 && 'b === 1 && 'c === 1)`)

## How was this patch tested?

Unit test in `FilterPushdownSuite`

Author: Sameer Agarwal <sameer@databricks.com>

Closes apache#11670 from sameeragarwal/combine-filters.
  • Loading branch information
sameeragarwal authored and roygao94 committed Mar 22, 2016
1 parent abfc8dd commit 12c8023
Show file tree
Hide file tree
Showing 2 changed files with 26 additions and 4 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -818,12 +818,19 @@ object CombineUnions extends Rule[LogicalPlan] {
}

/**
* Combines two adjacent [[Filter]] operators into one, merging the
* conditions into one conjunctive predicate.
* Combines two adjacent [[Filter]] operators into one, merging the non-redundant conditions into
* one conjunctive predicate.
*/
object CombineFilters extends Rule[LogicalPlan] {
object CombineFilters extends Rule[LogicalPlan] with PredicateHelper {
def apply(plan: LogicalPlan): LogicalPlan = plan transform {
case ff @ Filter(fc, nf @ Filter(nc, grandChild)) => Filter(And(nc, fc), grandChild)
case ff @ Filter(fc, nf @ Filter(nc, grandChild)) =>
(ExpressionSet(splitConjunctivePredicates(fc)) --
ExpressionSet(splitConjunctivePredicates(nc))).reduceOption(And) match {
case Some(ac) =>
Filter(And(ac, nc), grandChild)
case None =>
nf
}
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -81,6 +81,21 @@ class FilterPushdownSuite extends PlanTest {
comparePlans(optimized, correctAnswer)
}

test("combine redundant filters") {
val originalQuery =
testRelation
.where('a === 1 && 'b === 1)
.where('a === 1 && 'c === 1)

val optimized = Optimize.execute(originalQuery.analyze)
val correctAnswer =
testRelation
.where('a === 1 && 'b === 1 && 'c === 1)
.analyze

comparePlans(optimized, correctAnswer)
}

test("can't push without rewrite") {
val originalQuery =
testRelation
Expand Down

0 comments on commit 12c8023

Please sign in to comment.