static float calc_rank(float *w, tsvector * t, QUERYTYPE * q, int4 method) { ITEM *item = GETQUERY(q); float res = 0.0; int len; if (!t->size || !q->size) return 0.0; res = (item->type != VAL && item->val == (int4) '&') ? calc_rank_and(w, t, q) : calc_rank_or(w, t, q); if (res < 0) res = 1e-20; if ((method & RANK_NORM_LOGLENGTH) && t->size > 0) res /= log((double) (cnt_length(t) + 1)) / log(2.0); if (method & RANK_NORM_LENGTH) { len = cnt_length(t); if (len > 0) res /= (float) len; } if ((method & RANK_NORM_UNIQ) && t->size > 0) res /= (float) (t->size); if ((method & RANK_NORM_LOGUNIQ) && t->size > 0) res /= log((double) (t->size + 1)) / log(2.0); return res; }
static float calc_rank(float *w, TSVector t, TSQuery q, int32 method) { QueryItem *item = GETQUERY(q); float res = 0.0; int len; if (!t->size || !q->size) return 0.0; /* XXX: What about NOT? */ res = (item->type == QI_OPR && item->qoperator.oper == OP_AND) ? calc_rank_and(w, t, q) : calc_rank_or(w, t, q); if (res < 0) res = 1e-20f; if ((method & RANK_NORM_LOGLENGTH) && t->size > 0) res /= log((double) (cnt_length(t) + 1)) / log(2.0); if (method & RANK_NORM_LENGTH) { len = cnt_length(t); if (len > 0) res /= (float) len; } /* RANK_NORM_EXTDIST not applicable */ if ((method & RANK_NORM_UNIQ) && t->size > 0) res /= (float) (t->size); if ((method & RANK_NORM_LOGUNIQ) && t->size > 0) res /= log((double) (t->size + 1)) / log(2.0); if (method & RANK_NORM_RDIVRPLUS1) res /= (res + 1); return res; }
static float4 calc_rank_cd(float4 *arrdata, tsvector * txt, QUERYTYPE * query, int method) { DocRepresentation *doc; int len, i, doclen = 0; Extention ext; double Wdoc = 0.0; double invws[lengthof(weights)]; double SumDist = 0.0, PrevExtPos = 0.0, CurExtPos = 0.0; int NExtent = 0; for (i = 0; i < lengthof(weights); i++) { invws[i] = ((double) ((arrdata[i] >= 0) ? arrdata[i] : weights[i])); if (invws[i] > 1.0) ereport(ERROR, (errcode(ERRCODE_INVALID_PARAMETER_VALUE), errmsg("weight out of range"))); invws[i] = 1.0 / invws[i]; } doc = get_docrep(txt, query, &doclen); if (!doc) return 0.0; MemSet(&ext, 0, sizeof(Extention)); while (Cover(doc, doclen, query, &ext)) { double Cpos = 0.0; double InvSum = 0.0; int nNoise; DocRepresentation *ptr = ext.begin; while (ptr <= ext.end) { InvSum += invws[ptr->wclass]; ptr++; } Cpos = ((double) (ext.end - ext.begin + 1)) / InvSum; /* * if doc are big enough then ext.q may be equal to ext.p * due to limit of posional information. In this case we * approximate number of noise word as half cover's * length */ nNoise = (ext.q - ext.p) - (ext.end - ext.begin); if ( nNoise < 0 ) nNoise = (ext.end - ext.begin) / 2; Wdoc += Cpos / ((double) (1 + nNoise)); CurExtPos = ((double) (ext.q + ext.p)) / 2.0; if (NExtent > 0 && CurExtPos > PrevExtPos /* prevent devision by * zero in a case of multiple lexize */ ) SumDist += 1.0 / (CurExtPos - PrevExtPos); PrevExtPos = CurExtPos; NExtent++; } if ((method & RANK_NORM_LOGLENGTH) && txt->size > 0) Wdoc /= log((double) (cnt_length(txt) + 1)); if (method & RANK_NORM_LENGTH) { len = cnt_length(txt); if (len > 0) Wdoc /= (double) len; } if ((method & RANK_NORM_EXTDIST) && SumDist > 0) Wdoc /= ((double) NExtent) / SumDist; if ((method & RANK_NORM_UNIQ) && txt->size > 0) Wdoc /= (double) (txt->size); if ((method & RANK_NORM_LOGUNIQ) && txt->size > 0) Wdoc /= log((double) (txt->size + 1)) / log(2.0); for (i = 0; i < doclen; i++) if (doc[i].needfree) pfree(doc[i].item); pfree(doc); return (float4) Wdoc; }