98 bool case_insensitive);
100 bool case_insensitive,
101 int fixed_prefix_len);
256 bool collation_aware;
269 ((
Const *) rightop)->constisnull)
271 patt = (
Const *) rightop;
296 if (opfamily == TEXT_PATTERN_BTREE_FAM_OID)
298 eqopr = TextEqualOperator;
299 ltopr = TextPatternLessOperator;
300 geopr = TextPatternGreaterEqualOperator;
301 collation_aware =
false;
303 else if (opfamily == TEXT_SPGIST_FAM_OID)
305 eqopr = TextEqualOperator;
306 ltopr = TextPatternLessOperator;
307 geopr = TextPatternGreaterEqualOperator;
309 preopr = TextPrefixOperator;
310 collation_aware =
false;
314 eqopr = TextEqualOperator;
315 ltopr = TextLessOperator;
316 geopr = TextGreaterEqualOperator;
317 collation_aware =
true;
327 eqopr = NameEqualTextOperator;
328 ltopr = NameLessTextOperator;
329 geopr = NameGreaterEqualTextOperator;
330 collation_aware =
true;
334 if (opfamily == BPCHAR_PATTERN_BTREE_FAM_OID)
336 eqopr = BpcharEqualOperator;
337 ltopr = BpcharPatternLessOperator;
338 geopr = BpcharPatternGreaterEqualOperator;
339 collation_aware =
false;
343 eqopr = BpcharEqualOperator;
344 ltopr = BpcharLessOperator;
345 geopr = BpcharGreaterEqualOperator;
346 collation_aware =
true;
348 rdatatype = BPCHAROID;
351 eqopr = ByteaEqualOperator;
352 ltopr = ByteaLessOperator;
353 geopr = ByteaGreaterEqualOperator;
354 collation_aware =
false;
355 rdatatype = BYTEAOID;
372 rdatatype == BPCHAROID);
389 if (indexcollation != expr_coll)
430 if (collation_aware &&
459 (
Expr *) leftop, (
Expr *) greaterstr,
461 result =
lappend(result, expr);
502 Const *prefix = NULL;
504 double nullfrac = 0.0;
521 &vardata, &other, &varonleft))
523 if (!varonleft || !
IsA(other,
Const))
533 if (((
Const *) other)->constisnull)
538 constval = ((
Const *) other)->constvalue;
539 consttype = ((
Const *) other)->consttype;
547 if (consttype != TEXTOID && consttype != BYTEAOID)
565 eqopr = TextEqualOperator;
566 ltopr = TextLessOperator;
567 geopr = TextGreaterEqualOperator;
576 eqopr = NameEqualTextOperator;
577 ltopr = NameLessTextOperator;
578 geopr = NameGreaterEqualTextOperator;
582 eqopr = BpcharEqualOperator;
583 ltopr = BpcharLessOperator;
584 geopr = BpcharGreaterEqualOperator;
585 rdatatype = BPCHAROID;
588 eqopr = ByteaEqualOperator;
589 ltopr = ByteaLessOperator;
590 geopr = ByteaGreaterEqualOperator;
591 rdatatype = BYTEAOID;
607 nullfrac = stats->stanullfrac;
619 patt = (
Const *) other;
621 &prefix, &rest_selec);
629 if (prefix && prefix->
consttype != rdatatype)
632 rdatatype == BPCHAROID);
641 result =
var_eq_const(&vardata, eqopr, collation, prefix->constvalue,
701 double hist_weight = hist_size / 100.0;
703 selec = selec * hist_weight + heursel * (1.0 - hist_weight);
710 else if (selec > 0.9999)
728 selec *= 1.0 - nullfrac - sumcommon;
735 result = 1.0 - result - nullfrac;
771 elog(
ERROR,
"patternsel called for operator without a negator");
998 Assert(
typeid == BYTEAOID ||
typeid == TEXTOID);
1000 if (
typeid != BYTEAOID)
1003 pattlen = strlen(patt);
1010 patt = (
char *)
palloc(pattlen);
1015 match =
palloc(pattlen + 1);
1017 for (pos = 0; pos < pattlen; pos++)
1020 if (patt[pos] ==
'%' ||
1025 if (patt[pos] ==
'\\')
1032 match[match_pos++] = patt[pos];
1035 match[match_pos] =
'\0';
1037 if (
typeid != BYTEAOID)
1042 if (rest_selec != NULL)
1079 Assert(
typeid == BYTEAOID ||
typeid == TEXTOID);
1081 if (
typeid == BYTEAOID)
1083 (
errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
1084 errmsg(
"case insensitive matching not supported on type bytea")));
1093 (
errcode(ERRCODE_INDETERMINATE_COLLATION),
1094 errmsg(
"could not determine which collation to use for ILIKE"),
1095 errhint(
"Use the COLLATE clause to set the collation explicitly.")));
1107 if (wpatt[
wpos] ==
'%' ||
1112 if (wpatt[
wpos] ==
'\\')
1115 if (
wpos >= wpattlen)
1126 wmatch[wmatch_pos++] = wpatt[
wpos];
1129 wmatch[wmatch_pos] =
'\0';
1133 match[match_mblen] =
'\0';
1139 if (rest_selec != NULL)
1141 int wrestlen = wpattlen - wmatch_pos;
1155 if (
wpos == wpattlen)
1177 if (
typeid == BYTEAOID)
1179 (
errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
1180 errmsg(
"regular-expression matching not supported on type bytea")));
1184 case_insensitive, collation,
1189 *prefix_const = NULL;
1191 if (rest_selec != NULL)
1206 if (rest_selec != NULL)
1249 prefix, rest_selec);
1253 prefix, rest_selec);
1267 if (rest_selec != NULL)
1271 elog(
ERROR,
"unrecognized ptype: %d", (
int) ptype);
1304 Const *greaterstrcon;
1311 geopr, &opproc,
true,
true,
1313 prefixcon->constvalue,
1332 ltopr, &opproc,
false,
false,
1334 greaterstrcon->constvalue,
1362 eq_sel =
var_eq_const(vardata, eqopr, collation, prefixcon->constvalue,
1363 false,
true,
false);
1381#define FIXED_CHAR_SEL 0.20
1382#define CHAR_RANGE_SEL 0.25
1383#define ANY_CHAR_SEL 0.9
1384#define FULL_WILDCARD_SEL 5.0
1385#define PARTIAL_WILDCARD_SEL 2.0
1394 for (pos = 0; pos < pattlen; pos++)
1396 if (patt[pos] !=
'%' && patt[pos] !=
'_')
1400 for (; pos < pattlen; pos++)
1403 if (patt[pos] ==
'%')
1405 else if (patt[pos] ==
'_')
1407 else if (patt[pos] ==
'\\')
1428 int paren_depth = 0;
1435 for (pos = 0; pos < pattlen; pos++)
1437 if (patt[pos] ==
'(')
1439 if (paren_depth == 0)
1443 else if (patt[pos] ==
')' && paren_depth > 0)
1446 if (paren_depth == 0)
1448 pos - (paren_pos + 1),
1451 else if (patt[pos] ==
'|' && paren_depth == 0)
1458 pattlen - (pos + 1),
1462 else if (patt[pos] ==
'[')
1464 bool negclass =
false;
1466 if (patt[++pos] ==
'^')
1471 if (patt[pos] ==
']')
1473 while (pos < pattlen && patt[pos] !=
']')
1475 if (paren_depth == 0)
1478 else if (patt[pos] ==
'.')
1480 if (paren_depth == 0)
1483 else if (patt[pos] ==
'*' ||
1488 if (paren_depth == 0)
1491 else if (patt[pos] ==
'{')
1493 while (pos < pattlen && patt[pos] !=
'}')
1495 if (paren_depth == 0)
1498 else if (patt[pos] ==
'\\')
1504 if (paren_depth == 0)
1509 if (paren_depth == 0)
1521 int fixed_prefix_len)
1526 if (pattlen > 0 && patt[pattlen - 1] ==
'$' &&
1527 (pattlen == 1 || patt[pattlen - 2] !=
'\\'))
1544 if (fixed_prefix_len > 0)
1619 char *cmptxt = NULL;
1628 if (datatype == BYTEAOID)
1636 cmpstr = str_const->constvalue;
1640 if (datatype == NAMEOID)
1642 str_const->constvalue));
1645 len = strlen(workstr);
1647 cmpstr = str_const->constvalue;
1651 static char suffixchar = 0;
1652 static Oid suffixcollation = 0;
1654 if (!suffixchar || suffixcollation != collation)
1659 if (
varstr_cmp(best, 1,
"z", 1, collation) < 0)
1661 if (
varstr_cmp(best, 1,
"y", 1, collation) < 0)
1663 if (
varstr_cmp(best, 1,
"9", 1, collation) < 0)
1666 suffixcollation = collation;
1670 if (datatype == NAMEOID)
1673 memcpy(cmptxt, workstr,
len);
1674 cmptxt[
len] = suffixchar;
1675 cmptxt[
len + 1] =
'\0';
1690 if (datatype == BYTEAOID)
1699 unsigned char *lastchar;
1702 if (datatype == BYTEAOID)
1706 lastchar = (
unsigned char *) (workstr +
len - charlen);
1716 while (charinc(lastchar, charlen))
1718 Const *workstr_const;
1720 if (datatype == BYTEAOID)
1728 workstr_const->constvalue)))
1734 return workstr_const;
1739 pfree(workstr_const);
1747 workstr[
len] =
'\0';
1772 if (datatype == NAMEOID)
1774 else if (datatype == BYTEAOID)
1799 collation = DEFAULT_COLLATION_OID;
1804 collation = C_COLLATION_OID;
1814 elog(
ERROR,
"unexpected datatype in string_to_const: %u",
1819 return makeConst(datatype, -1, collation, constlen,
1820 conval,
false,
false);
#define CStringGetTextDatum(s)
#define TextDatumGetCString(d)
Datum byteain(PG_FUNCTION_ARGS)
#define OidIsValid(objectId)
Datum datumCopy(Datum value, bool typByVal, int typLen)
int errhint(const char *fmt,...)
int errcode(int sqlerrcode)
int errmsg(const char *fmt,...)
#define ereport(elevel,...)
Datum FunctionCall2Coll(FmgrInfo *flinfo, Oid collation, Datum arg1, Datum arg2)
void fmgr_info(Oid functionId, FmgrInfo *finfo)
#define DatumGetByteaPP(X)
#define PG_RETURN_FLOAT8(x)
#define DatumGetTextPP(X)
#define PG_GETARG_POINTER(n)
#define DirectFunctionCall1(func, arg1)
#define PG_GETARG_INT32(n)
#define PG_RETURN_POINTER(x)
#define PG_GET_COLLATION()
Assert(PointerIsAligned(start, uint64))
#define HeapTupleIsValid(tuple)
static void * GETSTRUCT(const HeapTupleData *tuple)
Datum icregexnesel(PG_FUNCTION_ARGS)
Datum regexnesel(PG_FUNCTION_ARGS)
static Node * like_regex_support(Node *rawreq, Pattern_Type ptype)
Datum iclikesel(PG_FUNCTION_ARGS)
Datum texticregexeq_support(PG_FUNCTION_ARGS)
static Selectivity prefix_selectivity(PlannerInfo *root, VariableStatData *vardata, Oid eqopr, Oid ltopr, Oid geopr, Oid collation, Const *prefixcon)
#define FULL_WILDCARD_SEL
Datum iclikejoinsel(PG_FUNCTION_ARGS)
Datum prefixjoinsel(PG_FUNCTION_ARGS)
static double patternsel(PG_FUNCTION_ARGS, Pattern_Type ptype, bool negate)
Datum regexeqsel(PG_FUNCTION_ARGS)
static Pattern_Prefix_Status pattern_fixed_prefix(Const *patt, Pattern_Type ptype, Oid collation, Const **prefix, Selectivity *rest_selec)
Datum likejoinsel(PG_FUNCTION_ARGS)
static Selectivity like_selectivity(const char *patt, int pattlen, bool case_insensitive)
Datum icregexnejoinsel(PG_FUNCTION_ARGS)
static List * match_pattern_prefix(Node *leftop, Node *rightop, Pattern_Type ptype, Oid expr_coll, Oid opfamily, Oid indexcollation)
Datum nlikejoinsel(PG_FUNCTION_ARGS)
static Datum string_to_datum(const char *str, Oid datatype)
Datum icnlikejoinsel(PG_FUNCTION_ARGS)
static Selectivity regex_selectivity_sub(const char *patt, int pattlen, bool case_insensitive)
Datum texticlike_support(PG_FUNCTION_ARGS)
Datum nlikesel(PG_FUNCTION_ARGS)
static Const * string_to_const(const char *str, Oid datatype)
#define PARTIAL_WILDCARD_SEL
Datum text_starts_with_support(PG_FUNCTION_ARGS)
static Const * string_to_bytea_const(const char *str, size_t str_len)
static Pattern_Prefix_Status like_fixed_prefix_ci(Const *patt_const, Oid collation, Const **prefix_const, Selectivity *rest_selec)
static Pattern_Prefix_Status regex_fixed_prefix(Const *patt_const, bool case_insensitive, Oid collation, Const **prefix_const, Selectivity *rest_selec)
static Const * make_greater_string(const Const *str_const, FmgrInfo *ltproc, Oid collation)
Datum icregexeqsel(PG_FUNCTION_ARGS)
Datum textlike_support(PG_FUNCTION_ARGS)
static Pattern_Prefix_Status like_fixed_prefix(Const *patt_const, Const **prefix_const, Selectivity *rest_selec)
Datum regexnejoinsel(PG_FUNCTION_ARGS)
static bool byte_increment(unsigned char *ptr, int len)
static double patternsel_common(PlannerInfo *root, Oid oprid, Oid opfuncid, List *args, int varRelid, Oid collation, Pattern_Type ptype, bool negate)
static Selectivity regex_selectivity(const char *patt, int pattlen, bool case_insensitive, int fixed_prefix_len)
Datum icnlikesel(PG_FUNCTION_ARGS)
Datum textregexeq_support(PG_FUNCTION_ARGS)
Datum prefixsel(PG_FUNCTION_ARGS)
static double patternjoinsel(PG_FUNCTION_ARGS, Pattern_Type ptype, bool negate)
Datum likesel(PG_FUNCTION_ARGS)
Datum regexeqjoinsel(PG_FUNCTION_ARGS)
Datum icregexeqjoinsel(PG_FUNCTION_ARGS)
List * lappend(List *list, void *datum)
RegProcedure get_opcode(Oid opno)
bool get_collation_isdeterministic(Oid colloid)
bool op_in_opfamily(Oid opno, Oid opfamily)
Oid get_negator(Oid opno)
Expr * make_opclause(Oid opno, Oid opresulttype, bool opretset, Expr *leftop, Expr *rightop, Oid opcollid, Oid inputcollid)
Const * makeConst(Oid consttype, int32 consttypmod, Oid constcollid, int constlen, Datum constvalue, bool constisnull, bool constbyval)
mbcharacter_incrementer pg_database_encoding_character_incrementer(void)
int pg_wchar2mb_with_len(const pg_wchar *from, char *to, int len)
int pg_mbcliplen(const char *mbstr, int len, int limit)
int pg_database_encoding_max_length(void)
int pg_mb2wchar_with_len(const char *from, pg_wchar *to, int len)
void pfree(void *pointer)
Datum nameout(PG_FUNCTION_ARGS)
Datum namein(PG_FUNCTION_ARGS)
Oid exprType(const Node *expr)
static bool is_opclause(const void *clause)
static bool is_funcclause(const void *clause)
#define IsA(nodeptr, _type_)
static int list_length(const List *l)
bool pg_iswcased(pg_wchar wc, pg_locale_t locale)
pg_locale_t pg_newlocale_from_collation(Oid collid)
FormData_pg_statistic * Form_pg_statistic
bool(* mbcharacter_incrementer)(unsigned char *mbstr, int len)
static bool DatumGetBool(Datum X)
static Datum PointerGetDatum(const void *X)
static char * DatumGetCString(Datum X)
static Pointer DatumGetPointer(Datum X)
static Datum CStringGetDatum(const char *X)
char * regexp_fixed_prefix(text *text_re, bool case_insensitive, Oid collation, bool *exact)
bool get_restriction_variable(PlannerInfo *root, List *args, int varRelid, VariableStatData *vardata, Node **other, bool *varonleft)
double var_eq_const(VariableStatData *vardata, Oid oproid, Oid collation, Datum constval, bool constisnull, bool varonleft, bool negate)
double mcv_selectivity(VariableStatData *vardata, FmgrInfo *opproc, Oid collation, Datum constval, bool varonleft, double *sumcommonp)
double ineq_histogram_selectivity(PlannerInfo *root, VariableStatData *vardata, Oid opoid, FmgrInfo *opproc, bool isgt, bool iseq, Oid collation, Datum constval, Oid consttype)
double histogram_selectivity(VariableStatData *vardata, FmgrInfo *opproc, Oid collation, Datum constval, bool varonleft, int min_hist_size, int n_skip, int *hist_size)
#define ReleaseVariableStats(vardata)
#define CLAMP_PROBABILITY(p)
#define DEFAULT_MATCH_SEL
void check_stack_depth(void)
static Size VARSIZE_ANY_EXHDR(const void *PTR)
static char * VARDATA(const void *PTR)
static char * VARDATA_ANY(const void *PTR)
static void SET_VARSIZE(void *PTR, Size len)
int varstr_cmp(const char *arg1, int len1, const char *arg2, int len2, Oid collid)