Skip to content

Commit

Permalink
evaluator: avoid evaluate independent subquery multiple times. (pingc…
Browse files Browse the repository at this point in the history
…ap#1144)

* evaluator: avoid evaluate independent subquery multiple times.

* ast: rename UseOuterContext to Correlated.
  • Loading branch information
coocood committed Apr 22, 2016
1 parent d78e404 commit 3b25069
Show file tree
Hide file tree
Showing 4 changed files with 11 additions and 12 deletions.
8 changes: 4 additions & 4 deletions ast/expressions.go
Original file line number Diff line number Diff line change
Expand Up @@ -250,10 +250,10 @@ type SubqueryExec interface {
type SubqueryExpr struct {
exprNode
// Query is the query SelectNode.
Query ResultSetNode
SubqueryExec SubqueryExec
Evaluated bool
UseOuterContext bool
Query ResultSetNode
SubqueryExec SubqueryExec
Evaluated bool
Correlated bool
}

// Accept implements Node Accept interface.
Expand Down
11 changes: 5 additions & 6 deletions evaluator/evaluator.go
Original file line number Diff line number Diff line change
Expand Up @@ -86,12 +86,7 @@ type Evaluator struct {

// Enter implements ast.Visitor interface.
func (e *Evaluator) Enter(in ast.Node) (out ast.Node, skipChildren bool) {
switch v := in.(type) {
case *ast.SubqueryExpr:
if v.Evaluated && !v.UseOuterContext {
// Subquery do not use outer context should only evaluate once.
return in, true
}
switch in.(type) {
case *ast.PatternInExpr, *ast.CompareSubqueryExpr:
e.multipleRows = true
case *ast.ExistsSubqueryExpr:
Expand Down Expand Up @@ -331,6 +326,10 @@ func (e *Evaluator) existsSubquery(v *ast.ExistsSubqueryExpr) bool {
// Evaluate SubqueryExpr.
// Get the value from v.SubQuery and set it to v.
func (e *Evaluator) subqueryExpr(v *ast.SubqueryExpr) bool {
if v.Evaluated && !v.Correlated {
// Subquery do not use outer context should only evaluate once.
return true
}
err := EvalSubquery(e.ctx, v, e.multipleRows, e.existRow)
if err != nil {
e.err = errors.Trace(err)
Expand Down
2 changes: 1 addition & 1 deletion executor/adapter.go
Original file line number Diff line number Diff line change
Expand Up @@ -140,7 +140,7 @@ func (e *subqueryExecutor) Leave(in ast.Node) (ast.Node, bool) {
case *ast.ExistsSubqueryExpr:
e.existRow = false
case *ast.SubqueryExpr:
if !x.UseOuterContext {
if !x.Correlated {
err := evaluator.EvalSubquery(e.ctx, x, e.multipleRows, e.existRow)
if err != nil {
e.err = errors.Trace(err)
Expand Down
2 changes: 1 addition & 1 deletion optimizer/resolver.go
Original file line number Diff line number Diff line change
Expand Up @@ -289,7 +289,7 @@ func (nr *nameResolver) Leave(inNode ast.Node) (node ast.Node, ok bool) {
if nr.useOuterContext {
// TODO: check this
// If there is a deep nest of subquery, there may be something wrong.
v.UseOuterContext = true
v.Correlated = true
nr.useOuterContext = false
}
case *ast.TruncateTableStmt:
Expand Down

0 comments on commit 3b25069

Please sign in to comment.