Changeset: ea0b21aeaf5b for MonetDB URL: https://dev.monetdb.org/hg/MonetDB/rev/ea0b21aeaf5b Modified Files: sql/server/rel_updates.c Branch: Jan2022 Log Message:
when inserting complex rows, convert into a union of rows. diffs (66 lines): diff --git a/sql/server/rel_updates.c b/sql/server/rel_updates.c --- a/sql/server/rel_updates.c +++ b/sql/server/rel_updates.c @@ -322,6 +322,7 @@ rel_inserts(mvc *sql, sql_table *t, sql_ sql_exp **inserts = insert_exp_array(sql, t, &len); list *exps = NULL; node *n, *m; + bool has_rel = false, all_values = true; if (r->exps) { if (!copy) { @@ -333,6 +334,8 @@ rel_inserts(mvc *sql, sql_table *t, sql_ return sql_error(sql, 02, SQLSTATE(42000) "%s: column '%s' specified more than once", action, c->base.name); if (!(inserts[c->colnr] = exp_check_type(sql, &c->type, r, e, type_equal))) return NULL; + has_rel = (has_rel || exp_has_rel(e)); + all_values &= is_values(e); } } else { for (m = collist->h; m; m = m->next) { @@ -344,6 +347,8 @@ rel_inserts(mvc *sql, sql_table *t, sql_ if (inserts[c->colnr]) return sql_error(sql, 02, SQLSTATE(42000) "%s: column '%s' specified more than once", action, c->base.name); inserts[c->colnr] = exp_ref(sql, e); + has_rel = has_rel || exp_has_rel(e); + all_values &= is_values(e); } } } @@ -384,10 +389,32 @@ rel_inserts(mvc *sql, sql_table *t, sql_ assert(inserts[c->colnr]); } } - /* now rewrite project exps in proper table order */ - exps = new_exp_list(sql->sa); - for (i = 0; i<len; i++) - list_append(exps, inserts[i]); + /* rewrite into unions */ + if (has_rel && rowcount && all_values) { + sql_rel *c = NULL; + for (size_t j = 0; j < rowcount; j++) { + sql_rel *p = rel_project(sql->sa, NULL, sa_list(sql->sa)); + for (m = ol_first_node(t->columns); m; m = m->next) { + sql_column *c = m->data; + sql_exp *e = inserts[c->colnr]; + assert(is_values(e)); + list *vals = e->f; + append(p->exps, list_fetch(vals, j)); + } + if (c) { + c = rel_setop(sql->sa, c, p, op_union); + rel_setop_set_exps(sql, c, rel_projections(sql, c->l, NULL, 1, 1), false); + } else + c = p; + } + r->l = c; + exps = rel_projections(sql, r->l, NULL, 1, 1); + } else { + /* now rewrite project exps in proper table order */ + exps = new_exp_list(sql->sa); + for (i = 0; i<len; i++) + list_append(exps, inserts[i]); + } return exps; } _______________________________________________ checkin-list mailing list -- checkin-list@monetdb.org To unsubscribe send an email to checkin-list-le...@monetdb.org