Changeset: f27c4caf0bac for MonetDB URL: https://dev.monetdb.org/hg/MonetDB?cmd=changeset;node=f27c4caf0bac Modified Files: sql/server/rel_statistics.c sql/server/rel_statistics.h Branch: properties Log Message:
Still making progress
diffs (truncated from 429 to 300 lines):
diff --git a/sql/server/rel_statistics.c b/sql/server/rel_statistics.c
--- a/sql/server/rel_statistics.c
+++ b/sql/server/rel_statistics.c
@@ -29,7 +29,8 @@ static sql_exp *
rel_propagate_column_ref_statistics(mvc *sql, sql_rel *rel, sql_exp *e)
{
atom *lval, *rval;
- sql_exp *ne = NULL;
+ sql_exp *found = NULL;
+ prop *p;
assert(e->type == e_column);
if (rel) {
@@ -39,12 +40,18 @@ rel_propagate_column_ref_statistics(mvc
case op_full:
case op_join:
case op_select:
- /* case op_anti: later */
+ case op_anti:
case op_semi: {
- bool found_with_semantics = false, found_left = false,
found_right = false, found_on_exps = false;
- sql_exp *ne = NULL;
+ bool found_with_semantics = false, found_left = false,
found_right = false;
- if (!list_empty(rel->exps)) { /* if there's an or, the
MIN and MAX get difficult to propagate */
+ /* propagate from the bottom first */
+ if (rel_propagate_column_ref_statistics(sql, rel->l, e))
+ found_left = true;
+ if (!found_left && is_join(rel->op) &&
rel_propagate_column_ref_statistics(sql, rel->r, e))
+ found_right = true;
+
+ assert(found_left || found_right);
+ if (!list_empty(rel->exps) && rel->op != op_anti) { /*
if there's an or, the MIN and MAX get difficult to propagate */
for (node *n = rel->exps->h ; n ; n = n->next) {
sql_exp *comp = n->data;
@@ -58,21 +65,14 @@ rel_propagate_column_ref_statistics(mvc
if ((lne =
comparison_find_column(le, e)) || (rne = comparison_find_column(re, e))) {
if
(e->semantics)
found_with_semantics = true;
- if
(is_outerjoin(rel->op)) {
- if
((lval = find_prop_and_get(lne ? le->p : re->p, PROP_MAX)))
-
set_max_property(sql, e, lval);
- if
((lval = find_prop_and_get(lne ? le->p : re->p, PROP_MIN)))
-
set_min_property(sql, e, lval);
- } else {
- if
((lval = find_prop_and_get(le->p, PROP_MAX)) &&
-
(rval = find_prop_and_get(re->p, PROP_MAX)))
-
set_max_property(sql, e, atom_min(lval, rval)); /* for equality reduce */
- if
((lval = find_prop_and_get(le->p, PROP_MIN)) &&
-
(rval = find_prop_and_get(re->p, PROP_MIN)))
-
set_min_property(sql, e, atom_max(lval, rval));
+ if
(!is_outerjoin(rel->op)) {
+ if
((lval = find_prop_and_get(le->p, PROP_MAX)) && (rval =
find_prop_and_get(re->p, PROP_MAX)))
+
set_property(sql, e, PROP_MAX, e->anti ? atom_max(lval, rval) : atom_min(lval,
rval)); /* for equality reduce */
+ if
((lval = find_prop_and_get(le->p, PROP_MIN)) && (rval =
find_prop_and_get(re->p, PROP_MIN)))
+
set_property(sql, e, PROP_MIN, e->anti ? atom_min(lval, rval) : atom_max(lval,
rval));
}
}
- ne = ne ? ne : lne ?
lne : rne;
+ found = found ? found :
lne ? lne : rne;
} break;
case cmp_notequal: {
sql_exp *le = comp->l,
*lne = NULL, *re = comp->r, *rne = NULL;
@@ -80,21 +80,14 @@ rel_propagate_column_ref_statistics(mvc
if ((lne =
comparison_find_column(le, e)) || (rne = comparison_find_column(re, e))) {
if
(e->semantics)
found_with_semantics = true;
- if
(is_outerjoin(rel->op)) {
- if
((lval = find_prop_and_get(lne ? le->p : re->p, PROP_MAX)))
-
set_max_property(sql, e, lval);
- if
((lval = find_prop_and_get(lne ? le->p : re->p, PROP_MIN)))
-
set_min_property(sql, e, lval);
- } else {
- if
((lval = find_prop_and_get(le->p, PROP_MAX)) &&
-
(rval = find_prop_and_get(re->p, PROP_MAX)))
-
set_max_property(sql, e, atom_max(lval, rval)); /* for inequality expand */
- if
((lval = find_prop_and_get(le->p, PROP_MIN)) &&
-
(rval = find_prop_and_get(re->p, PROP_MIN)))
-
set_min_property(sql, e, atom_min(lval, rval));
+ if
(!is_outerjoin(rel->op)) {
+ if
((lval = find_prop_and_get(le->p, PROP_MAX)) && (rval =
find_prop_and_get(re->p, PROP_MAX)))
+
set_property(sql, e, PROP_MAX, e->anti ? atom_min(lval, rval) : atom_max(lval,
rval)); /* for inequality expand */
+ if
((lval = find_prop_and_get(le->p, PROP_MIN)) && (rval =
find_prop_and_get(re->p, PROP_MIN)))
+
set_property(sql, e, PROP_MIN, e->anti ? atom_max(lval, rval) : atom_min(lval,
rval));
}
}
- ne = ne ? ne : lne ?
lne : rne;
+ found = found ? found :
lne ? lne : rne;
} break;
case cmp_gt:
case cmp_gte: {
@@ -103,65 +96,72 @@ rel_propagate_column_ref_statistics(mvc
if ((lne =
comparison_find_column(le, e)) || (rne = comparison_find_column(re, e)) || (fe
&& (fne = comparison_find_column(fe, e)))) {
if
(e->semantics)
found_with_semantics = true;
- if
(is_outerjoin(rel->op)) {
- if
((lval = find_prop_and_get(lne ? le->p : rne ? re->p : fe->p, PROP_MAX)))
-
set_max_property(sql, e, lval);
- if
((lval = find_prop_and_get(lne ? le->p : rne ? re->p : fe->p, PROP_MIN)))
-
set_min_property(sql, e, lval);
- } else if (lne)
{
- if (fe)
{ /* range case */
-
if (comp->flag & CMP_SYMMETRIC) {
-
if ((lval = find_prop_and_get(re->p, PROP_MIN)) && (rval =
find_prop_and_get(fe->p, PROP_MIN)))
-
set_max_property(sql, e, atom_min(lval, rval));
-
if ((lval = find_prop_and_get(re->p, PROP_MAX)) && (rval =
find_prop_and_get(fe->p, PROP_MAX)))
-
set_min_property(sql, e, atom_max(lval, rval));
+ if
(!is_outerjoin(rel->op)) {
+ if
(lne) {
+
if (fe) { /* range case */
+
if (comp->flag & CMP_SYMMETRIC) {
+
if ((lval = find_prop_and_get(re->p, PROP_MIN)) && (rval =
find_prop_and_get(fe->p, PROP_MIN))) {
+
atom *nmin = atom_min(lval, rval);
+
p = find_prop(e->p, PROP_MAX);
+
set_property(sql, e, PROP_MAX, p ? atom_max(nmin,
p->value) : nmin);
+
}
+
if ((lval = find_prop_and_get(re->p, PROP_MAX)) && (rval =
find_prop_and_get(fe->p, PROP_MAX))) {
+
atom *nmax = atom_max(lval, rval);
+
p = find_prop(e->p, PROP_MIN);
+
set_property(sql, e, PROP_MIN, p ? atom_min(nmax,
p->value) : nmax);
+
}
+
} else {
+
if ((lval = find_prop_and_get(fe->p, PROP_MIN)))
+
set_max_property(sql, e, lval);
+
if ((rval = find_prop_and_get(re->p, PROP_MAX)))
+
set_min_property(sql, e, rval);
+
}
} else {
-
if ((lval = find_prop_and_get(fe->p, PROP_MIN)))
-
set_max_property(sql, e, lval);
if ((rval = find_prop_and_get(re->p, PROP_MAX)))
set_min_property(sql, e, rval);
}
- } else {
-
if ((lval = find_prop_and_get(le->p, PROP_MAX)))
-
set_max_property(sql, e, lval);
-
if ((rval = find_prop_and_get(re->p, PROP_MAX)))
-
set_min_property(sql, e, rval);
- }
- } else if (rne)
{
- if (fe)
{ /* range case */
+ } else
if (rne) {
+
if (fe) { /* range case */
+
if (comp->flag & CMP_SYMMETRIC) {
+
if ((lval = find_prop_and_get(le->p, PROP_MIN)) && (rval =
find_prop_and_get(fe->p, PROP_MIN))) {
+
atom *nmin = atom_min(lval, rval);
+
p = find_prop(e->p, PROP_MAX);
+
set_property(sql, e, PROP_MAX, p ? atom_max(nmin,
p->value) : nmin);
+
}
+
if ((lval = find_prop_and_get(le->p, PROP_MAX)) && (rval =
find_prop_and_get(fe->p, PROP_MAX))) {
+
atom *nmax = atom_max(lval, rval);
+
p = find_prop(e->p, PROP_MIN);
+
set_property(sql, e, PROP_MIN, p ? atom_min(nmax,
p->value) : nmax);
+
}
+
} else {
+
if ((rval = find_prop_and_get(le->p, PROP_MIN)))
+
set_max_property(sql, e, rval);
+
}
+
} else {
+
if ((lval = find_prop_and_get(le->p, PROP_MIN)))
+
set_max_property(sql, e, lval);
+
}
+ } else
{ /* range case */
+
assert(fe);
if (comp->flag & CMP_SYMMETRIC) {
-
if ((lval = find_prop_and_get(le->p, PROP_MIN)) && (rval =
find_prop_and_get(fe->p, PROP_MIN)))
-
set_max_property(sql, e, atom_min(lval, rval));
-
if ((lval = find_prop_and_get(le->p, PROP_MAX)) && (rval =
find_prop_and_get(fe->p, PROP_MAX)))
-
set_min_property(sql, e, atom_max(lval, rval));
+
if ((lval = find_prop_and_get(le->p, PROP_MIN)) && (rval =
find_prop_and_get(re->p, PROP_MIN))) {
+
atom *nmin = atom_min(lval, rval);
+
p = find_prop(e->p, PROP_MAX);
+
set_property(sql, e, PROP_MAX, p ? atom_max(nmin, p->value) :
nmin);
+
}
+
if ((lval = find_prop_and_get(le->p, PROP_MAX)) && (rval =
find_prop_and_get(re->p, PROP_MAX))) {
+
atom *nmax = atom_max(lval, rval);
+
p = find_prop(e->p, PROP_MIN);
+
set_property(sql, e, PROP_MIN, p ? atom_min(nmax, p->value) :
nmax);
+
}
} else {
-
if ((lval = find_prop_and_get(re->p, PROP_MIN)))
-
set_max_property(sql, e, lval);
-
if ((rval = find_prop_and_get(le->p, PROP_MIN)))
+
if ((rval = find_prop_and_get(le->p, PROP_MAX)))
set_min_property(sql, e, rval);
}
- } else {
-
if ((lval = find_prop_and_get(le->p, PROP_MIN)))
-
set_max_property(sql, e, lval);
-
if ((rval = find_prop_and_get(re->p, PROP_MIN)))
-
set_min_property(sql, e, rval);
- }
- } else { /*
range case */
-
assert(fe);
- if
(comp->flag & CMP_SYMMETRIC) {
-
if ((lval = find_prop_and_get(le->p, PROP_MIN)) && (rval =
find_prop_and_get(re->p, PROP_MIN)))
-
set_max_property(sql, e, atom_min(lval, rval));
-
if ((lval = find_prop_and_get(le->p, PROP_MAX)) && (rval =
find_prop_and_get(re->p, PROP_MAX)))
-
set_min_property(sql, e, atom_max(lval, rval));
- } else {
-
if ((lval = find_prop_and_get(fe->p, PROP_MAX)))
-
set_max_property(sql, e, lval);
-
if ((rval = find_prop_and_get(le->p, PROP_MAX)))
-
set_min_property(sql, e, rval);
}
}
}
- ne = ne ? ne : lne ?
lne : rne ? rne : fne;
+ found = found ? found :
lne ? lne : rne ? rne : fne;
} break;
case cmp_lt:
case cmp_lte: {
@@ -171,24 +171,17 @@ rel_propagate_column_ref_statistics(mvc
if ((lne =
comparison_find_column(le, e)) || (rne = comparison_find_column(re, e))) {
if
(e->semantics)
found_with_semantics = true;
- if
(is_outerjoin(rel->op)) {
- if
((lval = find_prop_and_get(lne ? le->p : re->p, PROP_MAX)))
-
set_max_property(sql, e, lval);
- if
((lval = find_prop_and_get(lne ? le->p : re->p, PROP_MIN)))
-
set_min_property(sql, e, lval);
- } else if (lne)
{
- if
((lval = find_prop_and_get(re->p, PROP_MIN)))
-
set_max_property(sql, e, lval);
- if
((rval = find_prop_and_get(le->p, PROP_MIN)))
-
set_min_property(sql, e, rval);
- } else {
- if
((lval = find_prop_and_get(re->p, PROP_MAX)))
-
set_max_property(sql, e, lval);
- if
((rval = find_prop_and_get(le->p, PROP_MAX)))
-
set_min_property(sql, e, rval);
+ if
(!is_outerjoin(rel->op)) {
+ if
(lne) {
+
if ((lval = find_prop_and_get(re->p, PROP_MIN)))
+
set_max_property(sql, e, lval);
+ } else {
+
if ((rval = find_prop_and_get(le->p, PROP_MAX)))
+
set_min_property(sql, e, rval);
+ }
}
}
- ne = ne ? ne : lne ?
lne : rne;
+ found = found ? found :
lne ? lne : rne;
} break;
default: /* Maybe later I can
do cmp_in and cmp_notin */
break;
@@ -196,51 +189,39 @@ rel_propagate_column_ref_statistics(mvc
}
}
}
- if (ne)
- found_on_exps = true;
- if (!ne && (ne =
rel_propagate_column_ref_statistics(sql, rel->l, e)))
- found_left = true;
- if (!ne && is_join(rel->op) && (ne =
rel_propagate_column_ref_statistics(sql, rel->r, e)))
- found_right = true;
- if (ne) {
+ if (found) {
/* if semantics flag was found, null values
will pass */
- if (is_full(rel->op) || (is_left(rel->op) &&
found_right) || (is_right(rel->op) && found_left) || (has_nil(ne) &&
found_with_semantics))
+ if (is_full(rel->op) || (is_left(rel->op) &&
found_right) || (is_right(rel->op) && found_left) || (has_nil(e) &&
found_with_semantics))
set_has_nil(e);
- else if (found_on_exps && (!has_nil(ne) ||
!is_outerjoin(rel->op))) /* at an outer join, null values pass */
+ else if (!has_nil(e) || !is_outerjoin(rel->op))
/* at an outer join, null values pass */
set_has_no_nil(e);
}
- } break;
- /* case op_table: later */
- case op_basetable: {
- if (e->l && (ne = exps_bind_column2(rel->exps, e->l,
e->r, NULL))) {
- if ((lval = find_prop_and_get(ne->p, PROP_MAX)))
- set_max_property(sql, e, lval);
- if ((lval = find_prop_and_get(ne->p, PROP_MIN)))
- set_min_property(sql, e, lval);
- if (!has_nil(ne))
- set_has_no_nil(e);
- }
- } break;
+ return e;
+ }
+ case op_table:
+ case op_basetable:
case op_union:
case op_except:
case op_inter:
case op_project:
- case op_groupby: {
- ne = e->l ? exps_bind_column2(rel->exps, e->l, e->r,
NULL) : exps_bind_column(rel->exps, e->r, NULL, NULL, 1);
- if (ne) {
- if ((lval = find_prop_and_get(ne->p, PROP_MAX)))
- set_max_property(sql, e, lval);
- if ((lval = find_prop_and_get(ne->p, PROP_MIN)))
- set_min_property(sql, e, lval);
- if (!has_nil(ne))
+ case op_groupby:
+ if ((found = rel_find_exp(rel, e)) && rel->op !=
op_table) {
+ if ((lval = find_prop_and_get(found->p,
PROP_MAX)))
+ set_property(sql, e, PROP_MAX, lval);
+ if ((lval = find_prop_and_get(found->p,
PROP_MIN)))
_______________________________________________
checkin-list mailing list
[email protected]
https://www.monetdb.org/mailman/listinfo/checkin-list
