Changeset: 8afa8b5bcfbb for MonetDB URL: https://dev.monetdb.org/hg/MonetDB?cmd=changeset;node=8afa8b5bcfbb Modified Files: sql/server/rel_select.c sql/server/rel_unnest.c sql/test/analytics/Tests/analytics13.stable.err sql/test/miscellaneous/Tests/groupby_error.stable.out Branch: Oct2020 Log Message:
cleanup between, ie always use e_cmp / CMP_BETWEEN/CMP_SYMMETRIC only rewrite ifthenelse if we have freevars diffs (179 lines): diff --git a/sql/server/rel_select.c b/sql/server/rel_select.c --- a/sql/server/rel_select.c +++ b/sql/server/rel_select.c @@ -2244,8 +2244,9 @@ rel_logical_value_exp(sql_query *query, int symmetric = sc->data.lval->h->next->data.i_val; symbol *ro1 = sc->data.lval->h->next->next->data.sym; symbol *ro2 = sc->data.lval->h->next->next->next->data.sym; - sql_subtype *t1, *t2, *t3; - sql_exp *le, *re1, *re2, *e1 = NULL, *e2 = NULL; + sql_exp *le, *re1, *re2; + sql_subtype super; + assert(sc->data.lval->h->next->type == type_int); if (!(le = rel_value_exp(query, rel, lo, f, ek))) @@ -2255,44 +2256,23 @@ rel_logical_value_exp(sql_query *query, if (!(re2 = rel_value_exp(query, rel, ro2, f, ek))) return NULL; - t1 = exp_subtype(le); - t2 = exp_subtype(re1); - t3 = exp_subtype(re2); - - if (!t1 && (t2 || t3) && rel_binop_check_types(sql, rel ? *rel : NULL, le, t2 ? re1 : re2, 0) < 0) - return NULL; - if (!t2 && (t1 || t3) && rel_binop_check_types(sql, rel ? *rel : NULL, le, t1 ? le : re2, 0) < 0) - return NULL; - if (!t3 && (t1 || t2) && rel_binop_check_types(sql, rel ? *rel : NULL, le, t1 ? le : re1, 0) < 0) - return NULL; - - if (rel_convert_types(sql, rel ? *rel : NULL, rel ? *rel : NULL, &le, &re1, 1, type_equal) < 0 || - rel_convert_types(sql, rel ? *rel : NULL, rel ? *rel : NULL, &le, &re2, 1, type_equal) < 0) + supertype(&super, exp_subtype(re1), exp_subtype(le)); + supertype(&super, exp_subtype(re2), &super); + + if ((le = exp_check_type(sql, &super, rel ? *rel:NULL, le, type_equal)) == NULL || + (re1 = exp_check_type(sql, &super, rel ? *rel:NULL, re1, type_equal)) == NULL || + (re2 = exp_check_type(sql, &super, rel ? *rel:NULL, re2, type_equal)) == NULL) return NULL; if (!re1 || !re2) return NULL; - if (symmetric) { - sql_exp *tmp = NULL; - sql_subfunc *min, *max; - - if (rel_convert_types(sql, rel ? *rel : NULL, rel ? *rel : NULL, &re1, &re2, 1, type_equal) < 0) - return NULL; - min = sql_bind_func(sql->sa, sql->session->schema, "sql_min", exp_subtype(re1), exp_subtype(re2), F_FUNC); - max = sql_bind_func(sql->sa, sql->session->schema, "sql_max", exp_subtype(re1), exp_subtype(re2), F_FUNC); - if (!min || !max) - return sql_error(sql, 02, SQLSTATE(42000) "min or max operator on types %s %s missing", exp_subtype(re1)->type->sqlname, exp_subtype(re2)->type->sqlname); - tmp = exp_binop(sql->sa, re1, re2, min); - re2 = exp_binop(sql->sa, re1, re2, max); - re1 = tmp; - } - - if (!(e1 = rel_binop_(sql, rel ? *rel : NULL, le, re1, NULL, sc->token == SQL_NOT_BETWEEN ? "<" : ">=", card_value))) - return NULL; - if (!(e2 = rel_binop_(sql, rel ? *rel : NULL, le, re2, NULL, sc->token == SQL_NOT_BETWEEN ? ">" : "<=", card_value))) - return NULL; - return rel_binop_(sql, rel ? *rel : NULL, e1, e2, NULL, sc->token == SQL_NOT_BETWEEN ? "or" : "and", card_value); + le = exp_compare2(sql->sa, le, re1, re2, 3|CMP_BETWEEN); + if (sc->token == SQL_NOT_BETWEEN) + set_anti(le); + if (symmetric) + le->flag |= CMP_SYMMETRIC; + return le; } case SQL_IS_NULL: case SQL_IS_NOT_NULL: @@ -2523,7 +2503,7 @@ rel_logical_exp(sql_query *query, sql_re symbol *ro2 = sc->data.lval->h->next->next->next->data.sym; sql_exp *le, *re1, *re2; sql_subtype *t1, *t2, *t3; - int flag = 0; + int flag = (symmetric)?CMP_SYMMETRIC:0; assert(sc->data.lval->h->next->type == type_int); @@ -2552,41 +2532,7 @@ rel_logical_exp(sql_query *query, sql_re if (!re1 || !re2) return NULL; - /* for between 3 columns we use the between operator */ - if (symmetric && (le->card == CARD_ATOM || (re1->card == CARD_ATOM && re2->card == CARD_ATOM))) { - sql_exp *tmp = NULL; - sql_subfunc *min, *max; - - if (rel_convert_types(sql, rel, rel, &re1, &re2, 1, type_equal) < 0) - return NULL; - min = sql_bind_func(sql->sa, sql->session->schema, "sql_min", exp_subtype(re1), exp_subtype(re2), F_FUNC); - max = sql_bind_func(sql->sa, sql->session->schema, "sql_max", exp_subtype(re1), exp_subtype(re2), F_FUNC); - if (!min || !max) - return sql_error(sql, 02, SQLSTATE(42000) "min or max operator on types %s %s missing", exp_subtype(re1)->type->sqlname, exp_subtype(re2)->type->sqlname); - tmp = exp_binop(sql->sa, re1, re2, min); - re2 = exp_binop(sql->sa, re1, re2, max); - re1 = tmp; - symmetric = 0; - if (!re1 || !re2) - return NULL; - } - - flag = (symmetric)?CMP_SYMMETRIC:0; - - if (le->card == CARD_ATOM) { - sql_exp *e1, *e2; - if (!(e1 = rel_binop_(sql, rel, le, re1, NULL, sc->token == SQL_NOT_BETWEEN ? "<" : ">=", card_value))) - return NULL; - if (!(e2 = rel_binop_(sql, rel, le, re2, NULL, sc->token == SQL_NOT_BETWEEN ? ">" : "<=", card_value))) - return NULL; - if (!(e1 = rel_binop_(sql, rel, e1, e2, NULL, sc->token == SQL_NOT_BETWEEN ? "or" : "and", card_value))) - return NULL; - e2 = exp_compare(sql->sa, e1, exp_atom_bool(sql->sa, 1), cmp_equal); - return rel_select_push_exp_down(sql, rel, e2, le, le, re1, re1, re2, f); - } else { - rel = rel_compare_exp_(query, rel, le, re1, re2, 3|CMP_BETWEEN|flag, sc->token == SQL_NOT_BETWEEN ? 1 : 0, 0, f); - } - return rel; + return rel_compare_exp_(query, rel, le, re1, re2, 3|CMP_BETWEEN|flag, sc->token == SQL_NOT_BETWEEN ? 1 : 0, 0, f); } case SQL_IS_NULL: case SQL_IS_NOT_NULL: diff --git a/sql/server/rel_unnest.c b/sql/server/rel_unnest.c --- a/sql/server/rel_unnest.c +++ b/sql/server/rel_unnest.c @@ -2677,7 +2677,7 @@ rewrite_ifthenelse(visitor *v, sql_rel * sf = e->f; /* TODO also handle ifthenelse with more than 3 arguments */ - if (is_ifthenelse_func(sf) && !list_empty(e->l) && list_length(e->l) == 3) { + if (is_ifthenelse_func(sf) && !list_empty(e->l) && list_length(e->l) == 3 && rel_has_freevar(v->sql, rel)) { list *l = e->l; /* remove unecessary = true expressions under ifthenelse */ diff --git a/sql/test/analytics/Tests/analytics13.stable.err b/sql/test/analytics/Tests/analytics13.stable.err --- a/sql/test/analytics/Tests/analytics13.stable.err +++ b/sql/test/analytics/Tests/analytics13.stable.err @@ -30,8 +30,7 @@ QUERY = SELECT BETWEEN (SELECT tp2.proj * t1.col1 + MAX(t1.col5) FROM LATERAL (SELECT tp.ColID + MIN(t1.col6) - t1.col1 as proj FROM tbl_ProductSales tp) AS tp2) AND (SELECT SUM(t1.col7) FROM tbl_ProductSales tp HAVING t1.col2 < ALL(SELECT MAX(tp.ColID))) a2 -ERROR = !zero_or_one: cardinality violation, scalar expression expected -CODE = M0M29 +ERROR = !GDK reported error: hashjoin: more than one match # 14:18:27 > # 14:18:27 > "Done." diff --git a/sql/test/miscellaneous/Tests/groupby_error.stable.out b/sql/test/miscellaneous/Tests/groupby_error.stable.out --- a/sql/test/miscellaneous/Tests/groupby_error.stable.out +++ b/sql/test/miscellaneous/Tests/groupby_error.stable.out @@ -321,7 +321,7 @@ project ( % type, digits, scale, schema, table, column # name % varchar, int, int, str, str, str # type % 7, 1, 1, 0, 2, 2 # length -[ "tinyint", 1, 0, "", "%2", "%2" ] +[ "tinyint", 1, 0, "", "%1", "%1" ] [ "tinyint", 1, 0, NULL, NULL, NULL ] [ "tinyint", 1, 0, NULL, NULL, NULL ] #prepare select 1 from tab0 where ? between 1 and ?; @@ -330,7 +330,7 @@ project ( % type, digits, scale, schema, table, column # name % varchar, int, int, str, str, str # type % 7, 1, 1, 0, 2, 2 # length -[ "tinyint", 1, 0, "", "%2", "%2" ] +[ "tinyint", 1, 0, "", "%1", "%1" ] [ "tinyint", 1, 0, NULL, NULL, NULL ] [ "tinyint", 1, 0, NULL, NULL, NULL ] #prepare select 1 from tab0 where ? between ? and 1; @@ -339,7 +339,7 @@ project ( % type, digits, scale, schema, table, column # name % varchar, int, int, str, str, str # type % 7, 1, 1, 0, 2, 2 # length -[ "tinyint", 1, 0, "", "%2", "%2" ] +[ "tinyint", 1, 0, "", "%1", "%1" ] [ "tinyint", 1, 0, NULL, NULL, NULL ] [ "tinyint", 1, 0, NULL, NULL, NULL ] #prepare select EXISTS (SELECT ? FROM tab0) from tab0; _______________________________________________ checkin-list mailing list checkin-list@monetdb.org https://www.monetdb.org/mailman/listinfo/checkin-list