Partially undo commit 94da73281.

On closer inspection, mcv.c isn't as broken for ScalarArrayOpExpr
as I thought.  The Var-on-right issue is real enough, but actually
it does cope fine with a NULL array constant --- I was misled by
an XXX comment suggesting it didn't.  Undo that part of the code
change, and replace the XXX comment with something less misleading.
This commit is contained in:
Tom Lane 2022-08-05 15:57:46 -04:00
parent 3fe2fc6bbd
commit b9243cadad
2 changed files with 19 additions and 13 deletions

View File

@ -1452,7 +1452,6 @@ statext_is_compatible_clause_internal(PlannerInfo *root, Node *clause,
RangeTblEntry *rte = root->simple_rte_array[relid];
ScalarArrayOpExpr *expr = (ScalarArrayOpExpr *) clause;
Node *clause_expr;
Const *cst;
bool expronleft;
/* Only expressions with two arguments are considered compatible. */
@ -1460,11 +1459,11 @@ statext_is_compatible_clause_internal(PlannerInfo *root, Node *clause,
return false;
/* Check if the expression has the right shape (one Var, one Const) */
if (!examine_opclause_args(expr->args, &clause_expr, &cst, &expronleft))
if (!examine_opclause_args(expr->args, &clause_expr, NULL, &expronleft))
return false;
/* We only support Var on left and non-null array constants */
if (!expronleft || cst->constisnull)
/* We only support Var on left, Const on right */
if (!expronleft)
return false;
/*

View File

@ -1740,17 +1740,24 @@ mcv_get_match_bitmap(PlannerInfo *root, List *clauses,
if (!examine_opclause_args(expr->args, &clause_expr, &cst, &expronleft))
elog(ERROR, "incompatible clause");
/* We expect Var on left and non-null constant on right */
if (!expronleft || cst->constisnull)
/* We expect Var on left */
if (!expronleft)
elog(ERROR, "incompatible clause");
arrayval = DatumGetArrayTypeP(cst->constvalue);
get_typlenbyvalalign(ARR_ELEMTYPE(arrayval),
&elmlen, &elmbyval, &elmalign);
deconstruct_array(arrayval,
ARR_ELEMTYPE(arrayval),
elmlen, elmbyval, elmalign,
&elem_values, &elem_nulls, &num_elems);
/*
* Deconstruct the array constant, unless it's NULL (we'll cover
* that case below)
*/
if (!cst->constisnull)
{
arrayval = DatumGetArrayTypeP(cst->constvalue);
get_typlenbyvalalign(ARR_ELEMTYPE(arrayval),
&elmlen, &elmbyval, &elmalign);
deconstruct_array(arrayval,
ARR_ELEMTYPE(arrayval),
elmlen, elmbyval, elmalign,
&elem_values, &elem_nulls, &num_elems);
}
/* match the attribute/expression to a dimension of the statistic */
idx = mcv_match_expression(clause_expr, keys, exprs, &collid);