code: func Rewrite(r Rewriter, node Node) Node {
  	switch n := node.(type) {
  	case *Query:
  		n.Statements = Rewrite(r, n.Statements).(Statements)
  
  	case Statements:
  		for i, s := range n {
  			n[i] = Rewrite(r, s).(Statement)
  		}
  
  	case *SelectStatement:
  		n.Fields = Rewrite(r, n.Fields).(Fields)
  		n.Dimensions = Rewrite(r, n.Dimensions).(Dimensions)
  		n.Sources = Rewrite(r, n.Sources).(Sources)
  
  		// Rewrite may return nil. Nil does not satisfy the Expr
  		// interface. We only assert the rewritten result to be an
  		// Expr if it is not nil:
  		if cond := Rewrite(r, n.Condition); cond != nil {
  			n.Condition = cond.(Expr)
  		} else {
  			n.Condition = nil
  		}
  
  	case *SubQuery:
  		n.Statement = Rewrite(r, n.Statement).(*SelectStatement)
  
  	case Fields:
  		for i, f := range n {
  			n[i] = Rewrite(r, f).(*Field)
  		}
  
  	case *Field:
  		n.Expr = Rewrite(r, n.Expr).(Expr)
  
  	case Dimensions:
  		for i, d := range n {
  			n[i] = Rewrite(r, d).(*Dimension)
  		}
  
  	case *Dimension:
  		n.Expr = Rewrite(r, n.Expr).(Expr)
  
  	case *BinaryExpr:
  		n.LHS = Rewrite(r, n.LHS).(Expr)
  		n.RHS = Rewrite(r, n.RHS).(Expr)
  
  	case *ParenExpr:
  		n.Expr = Rewrite(r, n.Expr).(Expr)
  
  	case *Call:
  		for i, expr := range n.Args {
  			n.Args[i] = Rewrite(r, expr).(Expr)
  		}
  	}
  
  	return r.Rewrite(node)
  }
docs: // Rewrite recursively invokes the rewriter to replace each node.
  // Nodes are traversed depth-first and rewritten from leaf to root.