mirror of
https://github.com/postgres/postgres.git
synced 2025-05-11 05:41:32 +03:00
Further cleanup of indxpath logic related to IndexOptInfo.opfamily array.
We no longer need the terminating zero entry in opfamily[], so get rid of it. Also replace assorted ad-hoc looping logic with simple for and foreach constructs. This code is now noticeably more readable than it was an hour ago; credit to Robert for seeing that it could be simplified.
This commit is contained in:
parent
99bc012d51
commit
89a368418c
src
@ -1047,14 +1047,14 @@ group_clauses_by_indexkey(IndexOptInfo *index,
|
|||||||
{
|
{
|
||||||
List *clausegroup_list = NIL;
|
List *clausegroup_list = NIL;
|
||||||
bool found_outer_clause = false;
|
bool found_outer_clause = false;
|
||||||
int indexcol = 0;
|
int indexcol;
|
||||||
|
|
||||||
*found_clause = false; /* default result */
|
*found_clause = false; /* default result */
|
||||||
|
|
||||||
if (clauses == NIL && outer_clauses == NIL)
|
if (clauses == NIL && outer_clauses == NIL)
|
||||||
return NIL; /* cannot succeed */
|
return NIL; /* cannot succeed */
|
||||||
|
|
||||||
do
|
for (indexcol = 0; indexcol < index->ncolumns; indexcol++)
|
||||||
{
|
{
|
||||||
List *clausegroup = NIL;
|
List *clausegroup = NIL;
|
||||||
ListCell *l;
|
ListCell *l;
|
||||||
@ -1102,10 +1102,7 @@ group_clauses_by_indexkey(IndexOptInfo *index,
|
|||||||
return NIL;
|
return NIL;
|
||||||
|
|
||||||
clausegroup_list = lappend(clausegroup_list, clausegroup);
|
clausegroup_list = lappend(clausegroup_list, clausegroup);
|
||||||
|
}
|
||||||
indexcol++;
|
|
||||||
|
|
||||||
} while (indexcol < index->ncolumns);
|
|
||||||
|
|
||||||
if (!*found_clause && !found_outer_clause)
|
if (!*found_clause && !found_outer_clause)
|
||||||
return NIL; /* no indexable clauses anywhere */
|
return NIL; /* no indexable clauses anywhere */
|
||||||
@ -1163,8 +1160,8 @@ group_clauses_by_indexkey(IndexOptInfo *index,
|
|||||||
*
|
*
|
||||||
* 'index' is the index of interest.
|
* 'index' is the index of interest.
|
||||||
* 'indexcol' is a column number of 'index' (counting from 0).
|
* 'indexcol' is a column number of 'index' (counting from 0).
|
||||||
* 'opfamily' is the corresponding operator family.
|
|
||||||
* 'rinfo' is the clause to be tested (as a RestrictInfo node).
|
* 'rinfo' is the clause to be tested (as a RestrictInfo node).
|
||||||
|
* 'outer_relids' lists rels whose Vars can be considered pseudoconstant.
|
||||||
* 'saop_control' indicates whether ScalarArrayOpExpr clauses can be used.
|
* 'saop_control' indicates whether ScalarArrayOpExpr clauses can be used.
|
||||||
*
|
*
|
||||||
* Returns true if the clause can be used with this index key.
|
* Returns true if the clause can be used with this index key.
|
||||||
@ -1180,12 +1177,12 @@ match_clause_to_indexcol(IndexOptInfo *index,
|
|||||||
SaOpControl saop_control)
|
SaOpControl saop_control)
|
||||||
{
|
{
|
||||||
Expr *clause = rinfo->clause;
|
Expr *clause = rinfo->clause;
|
||||||
|
Oid opfamily = index->opfamily[indexcol];
|
||||||
Node *leftop,
|
Node *leftop,
|
||||||
*rightop;
|
*rightop;
|
||||||
Relids left_relids;
|
Relids left_relids;
|
||||||
Relids right_relids;
|
Relids right_relids;
|
||||||
Oid expr_op;
|
Oid expr_op;
|
||||||
Oid opfamily = index->opfamily[indexcol];
|
|
||||||
bool plain_op;
|
bool plain_op;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -1571,9 +1568,9 @@ matches_any_index(RestrictInfo *rinfo, RelOptInfo *rel, Relids outer_relids)
|
|||||||
foreach(l, rel->indexlist)
|
foreach(l, rel->indexlist)
|
||||||
{
|
{
|
||||||
IndexOptInfo *index = (IndexOptInfo *) lfirst(l);
|
IndexOptInfo *index = (IndexOptInfo *) lfirst(l);
|
||||||
int indexcol = 0;
|
int indexcol;
|
||||||
|
|
||||||
do
|
for (indexcol = 0; indexcol < index->ncolumns; indexcol++)
|
||||||
{
|
{
|
||||||
if (match_clause_to_indexcol(index,
|
if (match_clause_to_indexcol(index,
|
||||||
indexcol,
|
indexcol,
|
||||||
@ -1581,9 +1578,7 @@ matches_any_index(RestrictInfo *rinfo, RelOptInfo *rel, Relids outer_relids)
|
|||||||
outer_relids,
|
outer_relids,
|
||||||
SAOP_ALLOW))
|
SAOP_ALLOW))
|
||||||
return true;
|
return true;
|
||||||
|
}
|
||||||
indexcol++;
|
|
||||||
} while (indexcol < index->ncolumns);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
@ -1605,9 +1600,9 @@ eclass_matches_any_index(EquivalenceClass *ec, EquivalenceMember *em,
|
|||||||
foreach(l, rel->indexlist)
|
foreach(l, rel->indexlist)
|
||||||
{
|
{
|
||||||
IndexOptInfo *index = (IndexOptInfo *) lfirst(l);
|
IndexOptInfo *index = (IndexOptInfo *) lfirst(l);
|
||||||
int indexcol = 0;
|
int indexcol;
|
||||||
|
|
||||||
do
|
for (indexcol = 0; indexcol < index->ncolumns; indexcol++)
|
||||||
{
|
{
|
||||||
Oid curFamily = index->opfamily[indexcol];
|
Oid curFamily = index->opfamily[indexcol];
|
||||||
|
|
||||||
@ -1625,9 +1620,7 @@ eclass_matches_any_index(EquivalenceClass *ec, EquivalenceMember *em,
|
|||||||
list_member_oid(ec->ec_opfamilies, curFamily)) &&
|
list_member_oid(ec->ec_opfamilies, curFamily)) &&
|
||||||
match_index_to_operand((Node *) em->em_expr, indexcol, index))
|
match_index_to_operand((Node *) em->em_expr, indexcol, index))
|
||||||
return true;
|
return true;
|
||||||
|
}
|
||||||
indexcol++;
|
|
||||||
} while (indexcol < index->ncolumns);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
@ -2360,21 +2353,25 @@ List *
|
|||||||
expand_indexqual_conditions(IndexOptInfo *index, List *clausegroups)
|
expand_indexqual_conditions(IndexOptInfo *index, List *clausegroups)
|
||||||
{
|
{
|
||||||
List *resultquals = NIL;
|
List *resultquals = NIL;
|
||||||
ListCell *clausegroup_item;
|
ListCell *lc;
|
||||||
int indexcol = 0;
|
int indexcol;
|
||||||
|
|
||||||
if (clausegroups == NIL)
|
if (clausegroups == NIL)
|
||||||
return NIL;
|
return NIL;
|
||||||
|
|
||||||
clausegroup_item = list_head(clausegroups);
|
/* clausegroups must correspond to index columns */
|
||||||
do
|
Assert(list_length(clausegroups) <= index->ncolumns);
|
||||||
{
|
|
||||||
Oid curFamily = index->opfamily[indexcol];
|
|
||||||
ListCell *l;
|
|
||||||
|
|
||||||
foreach(l, (List *) lfirst(clausegroup_item))
|
indexcol = 0;
|
||||||
|
foreach(lc, clausegroups)
|
||||||
{
|
{
|
||||||
RestrictInfo *rinfo = (RestrictInfo *) lfirst(l);
|
List *clausegroup = (List *) lfirst(lc);
|
||||||
|
Oid curFamily = index->opfamily[indexcol];
|
||||||
|
ListCell *lc2;
|
||||||
|
|
||||||
|
foreach(lc2, clausegroup)
|
||||||
|
{
|
||||||
|
RestrictInfo *rinfo = (RestrictInfo *) lfirst(lc2);
|
||||||
Expr *clause = rinfo->clause;
|
Expr *clause = rinfo->clause;
|
||||||
|
|
||||||
/* First check for boolean cases */
|
/* First check for boolean cases */
|
||||||
@ -2426,12 +2423,8 @@ expand_indexqual_conditions(IndexOptInfo *index, List *clausegroups)
|
|||||||
(int) nodeTag(clause));
|
(int) nodeTag(clause));
|
||||||
}
|
}
|
||||||
|
|
||||||
clausegroup_item = lnext(clausegroup_item);
|
|
||||||
|
|
||||||
indexcol++;
|
indexcol++;
|
||||||
} while (clausegroup_item != NULL && indexcol < index->ncolumns);
|
}
|
||||||
|
|
||||||
Assert(clausegroup_item == NULL); /* else more groups than indexkeys */
|
|
||||||
|
|
||||||
return resultquals;
|
return resultquals;
|
||||||
}
|
}
|
||||||
|
@ -192,13 +192,13 @@ get_relation_info(PlannerInfo *root, Oid relationObjectId, bool inhparent,
|
|||||||
|
|
||||||
/*
|
/*
|
||||||
* Allocate per-column info arrays. To save a few palloc cycles
|
* Allocate per-column info arrays. To save a few palloc cycles
|
||||||
* we allocate all the Oid-type arrays in one request. Note that
|
* we allocate all the Oid-type arrays in one request. We must
|
||||||
* the opfamily array needs an extra, terminating zero at the end.
|
* pre-zero the sortop and nulls_first arrays in case the index is
|
||||||
* We pre-zero the ordering info in case the index is unordered.
|
* unordered.
|
||||||
*/
|
*/
|
||||||
info->indexkeys = (int *) palloc(sizeof(int) * ncolumns);
|
info->indexkeys = (int *) palloc(sizeof(int) * ncolumns);
|
||||||
info->opfamily = (Oid *) palloc0(sizeof(Oid) * (4 * ncolumns + 1));
|
info->opfamily = (Oid *) palloc0(sizeof(Oid) * (4 * ncolumns));
|
||||||
info->opcintype = info->opfamily + (ncolumns + 1);
|
info->opcintype = info->opfamily + ncolumns;
|
||||||
info->fwdsortop = info->opcintype + ncolumns;
|
info->fwdsortop = info->opcintype + ncolumns;
|
||||||
info->revsortop = info->fwdsortop + ncolumns;
|
info->revsortop = info->fwdsortop + ncolumns;
|
||||||
info->nulls_first = (bool *) palloc0(sizeof(bool) * ncolumns);
|
info->nulls_first = (bool *) palloc0(sizeof(bool) * ncolumns);
|
||||||
|
@ -427,9 +427,6 @@ typedef struct RelOptInfo
|
|||||||
*
|
*
|
||||||
* opfamily[], indexkeys[], opcintype[], fwdsortop[], revsortop[],
|
* opfamily[], indexkeys[], opcintype[], fwdsortop[], revsortop[],
|
||||||
* and nulls_first[] each have ncolumns entries.
|
* and nulls_first[] each have ncolumns entries.
|
||||||
* Note: for historical reasons, the opfamily array has an extra entry
|
|
||||||
* that is always zero. Some code scans until it sees a zero entry,
|
|
||||||
* rather than looking at ncolumns.
|
|
||||||
*
|
*
|
||||||
* Zeroes in the indexkeys[] array indicate index columns that are
|
* Zeroes in the indexkeys[] array indicate index columns that are
|
||||||
* expressions; there is one element in indexprs for each such column.
|
* expressions; there is one element in indexprs for each such column.
|
||||||
|
Loading…
x
Reference in New Issue
Block a user