diff options
Diffstat (limited to 'src/backend/utils/adt/selfuncs.c')
-rw-r--r-- | src/backend/utils/adt/selfuncs.c | 45 |
1 files changed, 45 insertions, 0 deletions
diff --git a/src/backend/utils/adt/selfuncs.c b/src/backend/utils/adt/selfuncs.c index 14b8c2ff545..6dd9fa2a598 100644 --- a/src/backend/utils/adt/selfuncs.c +++ b/src/backend/utils/adt/selfuncs.c @@ -105,6 +105,7 @@ #include "access/sysattr.h" #include "catalog/index.h" #include "catalog/pg_collation.h" +#include "catalog/pg_operator.h" #include "catalog/pg_opfamily.h" #include "catalog/pg_statistic.h" #include "catalog/pg_type.h" @@ -1440,6 +1441,50 @@ icnlikesel(PG_FUNCTION_ARGS) } /* + * boolvarsel - Selectivity of Boolean variable. + * + * This can actually be called on any boolean-valued expression. If it + * involves only Vars of the specified relation, and if there are statistics + * about the Var or expression (the latter is possible if it's indexed) then + * we'll produce a real estimate; otherwise it's just a default. + */ +Selectivity +boolvarsel(PlannerInfo *root, Node *arg, int varRelid) +{ + VariableStatData vardata; + double selec; + + examine_variable(root, arg, varRelid, &vardata); + if (HeapTupleIsValid(vardata.statsTuple)) + { + /* + * A boolean variable V is equivalent to the clause V = 't', so we + * compute the selectivity as if that is what we have. + */ + selec = var_eq_const(&vardata, BooleanEqualOperator, + BoolGetDatum(true), false, true); + } + else if (is_funcclause(arg)) + { + /* + * If we have no stats and it's a function call, estimate 0.3333333. + * This seems a pretty unprincipled choice, but Postgres has been + * using that estimate for function calls since 1992. The hoariness + * of this behavior suggests that we should not be in too much hurry + * to use another value. + */ + selec = 0.3333333; + } + else + { + /* Otherwise, the default estimate is 0.5 */ + selec = 0.5; + } + ReleaseVariableStats(vardata); + return selec; +} + +/* * booltestsel - Selectivity of BooleanTest Node. */ Selectivity |