99 bool case_insensitive);
101 bool case_insensitive,
102 int fixed_prefix_len);
259 bool collation_aware;
272 ((
Const *) rightop)->constisnull)
274 patt = (
Const *) rightop;
315 if (opfamily == TEXT_PATTERN_BTREE_FAM_OID)
317 eqopr = TextEqualOperator;
318 ltopr = TextPatternLessOperator;
319 geopr = TextPatternGreaterEqualOperator;
320 collation_aware =
false;
322 else if (opfamily == TEXT_SPGIST_FAM_OID)
324 eqopr = TextEqualOperator;
325 ltopr = TextPatternLessOperator;
326 geopr = TextPatternGreaterEqualOperator;
328 preopr = TextPrefixOperator;
329 collation_aware =
false;
333 eqopr = TextEqualOperator;
334 ltopr = TextLessOperator;
335 geopr = TextGreaterEqualOperator;
336 collation_aware =
true;
346 eqopr = NameEqualTextOperator;
347 ltopr = NameLessTextOperator;
348 geopr = NameGreaterEqualTextOperator;
349 collation_aware =
true;
353 if (opfamily == BPCHAR_PATTERN_BTREE_FAM_OID)
355 eqopr = BpcharEqualOperator;
356 ltopr = BpcharPatternLessOperator;
357 geopr = BpcharPatternGreaterEqualOperator;
358 collation_aware =
false;
362 eqopr = BpcharEqualOperator;
363 ltopr = BpcharLessOperator;
364 geopr = BpcharGreaterEqualOperator;
365 collation_aware =
true;
367 rdatatype = BPCHAROID;
370 eqopr = ByteaEqualOperator;
371 ltopr = ByteaLessOperator;
372 geopr = ByteaGreaterEqualOperator;
373 collation_aware =
false;
374 rdatatype = BYTEAOID;
391 rdatatype == BPCHAROID);
436 if (collation_aware &&
465 (
Expr *) leftop, (
Expr *) greaterstr,
467 result =
lappend(result, expr);
508 Const *prefix = NULL;
510 double nullfrac = 0.0;
527 &vardata, &other, &varonleft))
529 if (!varonleft || !
IsA(other,
Const))
539 if (((
Const *) other)->constisnull)
544 constval = ((
Const *) other)->constvalue;
545 consttype = ((
Const *) other)->consttype;
553 if (consttype != TEXTOID && consttype != BYTEAOID)
571 eqopr = TextEqualOperator;
572 ltopr = TextLessOperator;
573 geopr = TextGreaterEqualOperator;
582 eqopr = NameEqualTextOperator;
583 ltopr = NameLessTextOperator;
584 geopr = NameGreaterEqualTextOperator;
588 eqopr = BpcharEqualOperator;
589 ltopr = BpcharLessOperator;
590 geopr = BpcharGreaterEqualOperator;
591 rdatatype = BPCHAROID;
594 eqopr = ByteaEqualOperator;
595 ltopr = ByteaLessOperator;
596 geopr = ByteaGreaterEqualOperator;
597 rdatatype = BYTEAOID;
613 nullfrac = stats->stanullfrac;
625 patt = (
Const *) other;
627 &prefix, &rest_selec);
635 if (prefix && prefix->
consttype != rdatatype)
638 rdatatype == BPCHAROID);
647 result =
var_eq_const(&vardata, eqopr, collation, prefix->constvalue,
707 double hist_weight = hist_size / 100.0;
709 selec = selec * hist_weight + heursel * (1.0 - hist_weight);
716 else if (selec > 0.9999)
734 selec *= 1.0 - nullfrac - sumcommon;
741 result = 1.0 - result - nullfrac;
777 elog(
ERROR,
"patternsel called for operator without a negator");
1004 bool locale_is_c =
false;
1007 Assert(
typeid == BYTEAOID ||
typeid == TEXTOID);
1009 if (case_insensitive)
1011 if (
typeid == BYTEAOID)
1013 (
errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
1014 errmsg(
"case insensitive matching not supported on type bytea")));
1023 (
errcode(ERRCODE_INDETERMINATE_COLLATION),
1024 errmsg(
"could not determine which collation to use for ILIKE"),
1025 errhint(
"Use the COLLATE clause to set the collation explicitly.")));
1035 if (
typeid != BYTEAOID)
1038 pattlen = strlen(patt);
1045 patt = (
char *)
palloc(pattlen);
1050 match =
palloc(pattlen + 1);
1052 for (pos = 0; pos < pattlen; pos++)
1055 if (patt[pos] ==
'%' ||
1060 if (patt[pos] ==
'\\')
1068 if (case_insensitive &&
1072 match[match_pos++] = patt[pos];
1075 match[match_pos] =
'\0';
1077 if (
typeid != BYTEAOID)
1082 if (rest_selec != NULL)
1112 if (
typeid == BYTEAOID)
1114 (
errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
1115 errmsg(
"regular-expression matching not supported on type bytea")));
1119 case_insensitive, collation,
1124 *prefix_const = NULL;
1126 if (rest_selec != NULL)
1141 if (rest_selec != NULL)
1177 prefix, rest_selec);
1181 prefix, rest_selec);
1185 prefix, rest_selec);
1189 prefix, rest_selec);
1203 if (rest_selec != NULL)
1207 elog(
ERROR,
"unrecognized ptype: %d", (
int) ptype);
1240 Const *greaterstrcon;
1247 geopr, &opproc,
true,
true,
1249 prefixcon->constvalue,
1268 ltopr, &opproc,
false,
false,
1270 greaterstrcon->constvalue,
1298 eq_sel =
var_eq_const(vardata, eqopr, collation, prefixcon->constvalue,
1299 false,
true,
false);
1317 #define FIXED_CHAR_SEL 0.20
1318 #define CHAR_RANGE_SEL 0.25
1319 #define ANY_CHAR_SEL 0.9
1320 #define FULL_WILDCARD_SEL 5.0
1321 #define PARTIAL_WILDCARD_SEL 2.0
1330 for (pos = 0; pos < pattlen; pos++)
1332 if (patt[pos] !=
'%' && patt[pos] !=
'_')
1336 for (; pos < pattlen; pos++)
1339 if (patt[pos] ==
'%')
1341 else if (patt[pos] ==
'_')
1343 else if (patt[pos] ==
'\\')
1364 int paren_depth = 0;
1371 for (pos = 0; pos < pattlen; pos++)
1373 if (patt[pos] ==
'(')
1375 if (paren_depth == 0)
1379 else if (patt[pos] ==
')' && paren_depth > 0)
1382 if (paren_depth == 0)
1384 pos - (paren_pos + 1),
1387 else if (patt[pos] ==
'|' && paren_depth == 0)
1394 pattlen - (pos + 1),
1398 else if (patt[pos] ==
'[')
1400 bool negclass =
false;
1402 if (patt[++pos] ==
'^')
1407 if (patt[pos] ==
']')
1409 while (pos < pattlen && patt[pos] !=
']')
1411 if (paren_depth == 0)
1414 else if (patt[pos] ==
'.')
1416 if (paren_depth == 0)
1419 else if (patt[pos] ==
'*' ||
1424 if (paren_depth == 0)
1427 else if (patt[pos] ==
'{')
1429 while (pos < pattlen && patt[pos] !=
'}')
1431 if (paren_depth == 0)
1434 else if (patt[pos] ==
'\\')
1440 if (paren_depth == 0)
1445 if (paren_depth == 0)
1457 int fixed_prefix_len)
1462 if (pattlen > 0 && patt[pattlen - 1] ==
'$' &&
1463 (pattlen == 1 || patt[pattlen - 2] !=
'\\'))
1480 if (fixed_prefix_len > 0)
1506 return (
c >=
'A' &&
c <=
'Z') || (
c >=
'a' &&
c <=
'z');
1509 else if (
locale &&
locale->provider == COLLPROVIDER_ICU)
1511 (
c >=
'A' &&
c <=
'Z') || (
c >=
'a' &&
c <=
'z');
1512 else if (
locale &&
locale->provider == COLLPROVIDER_LIBC)
1515 return isalpha((
unsigned char)
c);
1580 char *cmptxt = NULL;
1589 if (datatype == BYTEAOID)
1597 cmpstr = str_const->constvalue;
1601 if (datatype == NAMEOID)
1603 str_const->constvalue));
1606 len = strlen(workstr);
1608 cmpstr = str_const->constvalue;
1612 static char suffixchar = 0;
1613 static Oid suffixcollation = 0;
1615 if (!suffixchar || suffixcollation != collation)
1620 if (
varstr_cmp(best, 1,
"z", 1, collation) < 0)
1622 if (
varstr_cmp(best, 1,
"y", 1, collation) < 0)
1624 if (
varstr_cmp(best, 1,
"9", 1, collation) < 0)
1627 suffixcollation = collation;
1631 if (datatype == NAMEOID)
1634 memcpy(cmptxt, workstr,
len);
1635 cmptxt[
len] = suffixchar;
1636 cmptxt[
len + 1] =
'\0';
1651 if (datatype == BYTEAOID)
1660 unsigned char *lastchar;
1663 if (datatype == BYTEAOID)
1667 lastchar = (
unsigned char *) (workstr +
len - charlen);
1677 while (charinc(lastchar, charlen))
1679 Const *workstr_const;
1681 if (datatype == BYTEAOID)
1689 workstr_const->constvalue)))
1695 return workstr_const;
1700 pfree(workstr_const);
1708 workstr[
len] =
'\0';
1733 if (datatype == NAMEOID)
1735 else if (datatype == BYTEAOID)
1760 collation = DEFAULT_COLLATION_OID;
1765 collation = C_COLLATION_OID;
1775 elog(
ERROR,
"unexpected datatype in string_to_const: %u",
1780 return makeConst(datatype, -1, collation, constlen,
1781 conval,
false,
false);
#define CStringGetTextDatum(s)
#define TextDatumGetCString(d)
#define IS_HIGHBIT_SET(ch)
#define OidIsValid(objectId)
Datum datumCopy(Datum value, bool typByVal, int typLen)
elog(ERROR, "%s: %s", p2, msg)
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()
#define HeapTupleIsValid(tuple)
Assert(fmt[strlen(fmt) - 1] !='\n')
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 Pattern_Prefix_Status like_fixed_prefix(Const *patt_const, bool case_insensitive, Oid collation, Const **prefix_const, Selectivity *rest_selec)
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 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 int pattern_char_isalpha(char c, bool is_multibyte, pg_locale_t locale, bool locale_is_c)
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_mbcliplen(const char *mbstr, int len, int limit)
int pg_database_encoding_max_length(void)
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 lc_collate_is_c(Oid collation)
pg_locale_t pg_newlocale_from_collation(Oid collid)
bool lc_ctype_is_c(Oid collation)
FormData_pg_statistic * Form_pg_statistic
bool(* mbcharacter_incrementer)(unsigned char *mbstr, int len)
void check_stack_depth(void)
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
struct PlannerInfo * root
#define SET_VARSIZE(PTR, len)
#define VARSIZE_ANY_EXHDR(PTR)
int varstr_cmp(const char *arg1, int len1, const char *arg2, int len2, Oid collid)
Datum byteain(PG_FUNCTION_ARGS)