예제 #1
0
        unsafe private bool GetNext(WordIndexForQuery fstWifq,
                                    ref OriginalDocumentPositionList fstODPL, ref Entity.DocumentPositionList fstDPL)
        {
            fstWifq.WordIndex.GetNextOriginal(ref fstODPL);
            fstODPL.ToDocumentPositionList(ref fstDPL);

            return(fstODPL.DocumentId >= 0);

#if a
            if (!_HasRandField)
            {
            }
            else
            {
                if (_CurDocidPayloadIndex >= _CurDocidPayloadsCount)
                {
                    _CurDocidPayloadsCount = LoadDocIdPayloads();

                    if (_CurDocidPayloadsCount <= 0)
                    {
                        fstODPL.DocumentId = -1;
                        return;
                        //return new OriginalDocumentPositionList(-1);
                    }
                }

                fstODPL.DocumentId        = _DocidPayloads[_CurDocidPayloadIndex].DocumentId;
                fstODPL.CountAndWordCount = _DocidPayloads[_CurDocidPayloadIndex].CountAndWordCount;
                //odpl = _DocidPayloads[_CurDocidPayloadIndex++];
                _CurDocidPayloadIndex++;
                return(true);
            }
#endif
        }
예제 #2
0
        public bool GetNextOriginal(ref OriginalDocumentPositionList odpl)
        {
            if (_IndexReader == null)
            {
                odpl.DocumentId = -1;
                return(false);
            }

            return(_IndexReader.GetNextOriginal(ref odpl));
        }
예제 #3
0
        public OriginalDocumentPositionList GetNextOriginal()
        {
            if (_IndexReader == null)
            {
                return(new OriginalDocumentPositionList(-1));
            }

            OriginalDocumentPositionList odpl = new OriginalDocumentPositionList();

            _IndexReader.GetNextOriginal(ref odpl);
            return(odpl);
        }
예제 #4
0
        unsafe private void TestFillPayloadRank(string tableName)
        {
            OutputMessage("TestGetDocIdReplaceFieldValue");

            AddColumn("Times");
            AddColumn("Elapse(ms)");
            AddColumn("ElapseOneTime(ms)");

            Data.DBProvider dbProvider = Data.DBProvider.GetDBProvider(Parameters[0], false);

            if (dbProvider == null)
            {
                throw new DataException(string.Format("Table name {0} does not exist!", Parameters[0]));
            }

            Random rand      = new Random();
            int    count     = 1000000;
            int    lastDocId = dbProvider.LastDocId;

            OriginalDocumentPositionList[] payloads = new OriginalDocumentPositionList[count];

            for (int i = 0; i < payloads.Length; i++)
            {
                payloads[i] = new OriginalDocumentPositionList(i * 10);
                payloads[i].CountAndWordCount = 1;
            }

            payloads[0].DocumentId = 8 * payloads.Length;

            Data.Field rankField = dbProvider.GetField("Rank");
            int        tab       = rankField.TabIndex;

            Stopwatch sw = new Stopwatch();

            //int docid = rand.Next(lastDocId);
            sw.Start();

            for (int j = 0; j < count / payloads.Length; j++)
            {
                dbProvider.FillPayloadRank(tab, count, payloads);
            }
            sw.Stop();

            OutputValue("Times", count);
            OutputValue("Elapse(ms)", sw.ElapsedMilliseconds);
            OutputValue("ElapseOneTime(ms)", (double)sw.ElapsedMilliseconds / count);
        }
예제 #5
0
        /// <summary>
        /// Get next original document position list
        /// </summary>
        /// <returns>if end of the index, docid of result is -1</returns>
        public bool GetNextOriginal(ref OriginalDocumentPositionList odpl)
        {
            if (_End)
            {
                odpl.DocumentId = -1;
                return(false);
                //return new OriginalDocumentPositionList(-1);
            }

            if (_CurrentDocId < 0)
            {
                if (!NextFileIndex())
                {
                    //End of the index
                    odpl.DocumentId = -1;
                    return(false);
                    //return new OriginalDocumentPositionList(-1);
                }
            }

            if (_CurrentIndexBuf.Position < _CurrentIndexBuf.Start + _CurrentIndexBuf.Length)
            {
                DocumentPositionList.GetNextOriginalDocumentPositionList(ref odpl, ref _CurrentDocId,
                                                                         _CurrentIndexBuf, _WordStepDocIndex.SimpleMode);
                return(true);
            }
            else
            {
                if (!NextFileIndexBuf())
                {
                    odpl.DocumentId = -1;
                    return(false);
                    //return new OriginalDocumentPositionList(-1);
                }

                DocumentPositionList.GetNextOriginalDocumentPositionList(ref odpl, ref _CurrentDocId,
                                                                         _CurrentIndexBuf, _WordStepDocIndex.SimpleMode);
                return(true);
            }
        }
예제 #6
0
        unsafe private void CalculateWithPosition(Core.SFQL.Parse.DocumentResultWhereDictionary upDict,
                                                  ref Core.SFQL.Parse.DocumentResultWhereDictionary docIdRank, WordIndexForQuery[] wordIndexes)
        {
            if (UseMatch(wordIndexes))
            {
                CalculateWithPositionMatch(upDict, ref docIdRank, wordIndexes);
                return;
            }

            Array.Sort(wordIndexes);

            AdjustSort(wordIndexes);

            MinResultCount = _DBProvider.Table.GroupByLimit;

            //Get max word doc list count
            int minWordDocListCount = 1 * 1024 * 1024; //1M

            foreach (WordIndexForQuery wifq in wordIndexes)
            {
                minWordDocListCount = Math.Min(minWordDocListCount, wifq.WordIndex.Count);
            }


            Query.PerformanceReport performanceReport = new Hubble.Core.Query.PerformanceReport("Calculate");

            //Merge
            bool oneWordOptimize = this._QueryParameter.CanLoadPartOfDocs && this._QueryParameter.AndExpressionCanBeOptimized(_DBProvider) &&
                                   wordIndexes.Length == 1 && _NotInDict == null && _QueryParameter.End >= 0 && !_QueryParameter.NeedDistinct;

            if (oneWordOptimize)
            {
                IQueryOptimize qOptimize = QueryOptimizeBuilder.Build(typeof(OneWordOptimize),
                                                                      DBProvider, _QueryParameter.End, _QueryParameter.OrderBy,
                                                                      _QueryParameter.OrderBys, _QueryParameter.NeedGroupBy,
                                                                      _QueryParameter.OrderByCanBeOptimized, _QueryParameter.NeedFilterUntokenizedConditions(this._DBProvider),
                                                                      _QueryParameter.UntokenizedTreeOnRoot, wordIndexes);

                try
                {
                    qOptimize.CalculateOptimize(upDict, ref docIdRank);
                    return;
                }
                finally
                {
                    performanceReport.Stop();
                }
            }

            if (this._QueryParameter.CanLoadPartOfDocs && this._QueryParameter.AndExpressionCanBeOptimized(_DBProvider) &&
                _NotInDict == null && _QueryParameter.End >= 0 && !_QueryParameter.NeedDistinct)
            {
                IQueryOptimize qOptimize = QueryOptimizeBuilder.Build(typeof(ContainsOptimize),
                                                                      DBProvider, _QueryParameter.End, _QueryParameter.OrderBy,
                                                                      _QueryParameter.OrderBys, _QueryParameter.NeedGroupBy,
                                                                      _QueryParameter.OrderByCanBeOptimized, _QueryParameter.NeedFilterUntokenizedConditions(this._DBProvider),
                                                                      _QueryParameter.UntokenizedTreeOnRoot, wordIndexes);

                try
                {
                    qOptimize.CalculateOptimize(upDict, ref docIdRank);
                    return;
                }
                finally
                {
                    performanceReport.Stop();
                }

                //if (qOptimize.Argument.IsOrderByScoreDesc())
                //{

                //}
            }

            if (docIdRank.Count == 0)
            {
                if (minWordDocListCount > DocumentResultWhereDictionary.DefaultSize)
                {
                    docIdRank = new Core.SFQL.Parse.DocumentResultWhereDictionary(minWordDocListCount);
                }
            }

            {
                double ratio = 1;

                if (wordIndexes.Length > 1)
                {
                    ratio = (double)2 / (double)(wordIndexes.Length - 1);
                }

                int wordIndexesLen = wordIndexes.Length;

                WordIndexForQuery fstWifq = wordIndexes[0]; //first word

                OriginalDocumentPositionList fstODPL = new OriginalDocumentPositionList();
                fstWifq.WordIndex.GetNextOriginal(ref fstODPL);

                //Entity.DocumentPositionList fstDocList = fstWifq.WordIndex.GetNext();

                Entity.DocumentPositionList[] docListArr = new Hubble.Core.Entity.DocumentPositionList[wordIndexesLen];

                //docListArr[0] = fstDocList;
                fstODPL.ToDocumentPositionList(ref docListArr[0]);

                OriginalDocumentPositionList odpl = new OriginalDocumentPositionList();

                while (fstODPL.DocumentId >= 0)
                {
                    int curWord    = 1;
                    int firstDocId = fstODPL.DocumentId;

                    while (curWord < wordIndexesLen)
                    {
                        //docListArr[curWord] = wordIndexes[curWord].WordIndex.Get(firstDocId);

                        wordIndexes[curWord].WordIndex.GetNextOriginalWithDocId(ref odpl, firstDocId);
                        odpl.ToDocumentPositionList(ref docListArr[curWord]);

                        if (docListArr[curWord].DocumentId < 0)
                        {
                            if ((wordIndexes[curWord].Flags & WordInfo.Flag.Or) != 0)
                            {
                                curWord++;
                                continue;
                            }
                            else
                            {
                                break;
                            }
                        }

                        curWord++;
                    } //While

                    if (curWord >= wordIndexesLen)
                    {
                        //Matched
                        //Caculate score

                        long totalScore = 0;
                        Entity.DocumentPositionList lastDocList
                            = new Hubble.Core.Entity.DocumentPositionList();

                        for (int i = 0; i < wordIndexesLen; i++)
                        {
                            WordIndexForQuery wifq = wordIndexes[i];

                            if (wifq.WordIndex.Count == 0)
                            {
                                //a^5000^0 b^5000^2^1
                                //if has a and hasn't b but b can be or
                                //2010-09-30 eaglet
                                continue;
                            }

                            Entity.DocumentPositionList docList = docListArr[i];


                            long score = (long)wifq.FieldRank * (long)wifq.WordRank * (long)wifq.Idf_t * (long)docList.Count * (long)1000000 / ((long)wifq.Sum_d_t * (long)docList.TotalWordsInThisDocument);

                            if (score < 0)
                            {
                                //Overflow
                                score = long.MaxValue - 4000000;
                            }

                            double delta = 1;

                            if (i > 0)
                            {
                                //Calculate with position
                                double queryPositionDelta = wifq.FirstPosition - wordIndexes[i - 1].FirstPosition;
                                double positionDelta      = docList.FirstPosition - lastDocList.FirstPosition;

                                delta = Math.Abs(queryPositionDelta - positionDelta);

                                if (delta < 0.031)
                                {
                                    delta = 0.031;
                                }
                                else if (delta <= 1.1)
                                {
                                    delta = 0.5;
                                }
                                else if (delta <= 2.1)
                                {
                                    delta = 1;
                                }

                                delta = Math.Pow((1 / delta), ratio) * docList.Count * lastDocList.Count /
                                        (double)(wifq.QueryCount * wordIndexes[i - 1].QueryCount);
                            }

                            lastDocList = docList;

                            totalScore += (long)(score * delta);
                        }

                        bool notInDict = false;

                        if (_NotInDict != null)
                        {
                            if (_NotInDict.ContainsKey(firstDocId))
                            {
                                notInDict = true;
                            }
                        }

                        if (!notInDict)
                        {
                            if (upDict == null)
                            {
                                docIdRank.Add(firstDocId, totalScore);
                            }
                            else
                            {
                                if (!upDict.Not)
                                {
                                    if (upDict.ContainsKey(firstDocId))
                                    {
                                        docIdRank.Add(firstDocId, totalScore);
                                    }
                                }
                                else
                                {
                                    if (!upDict.ContainsKey(firstDocId))
                                    {
                                        docIdRank.Add(firstDocId, totalScore);
                                    }
                                }
                            }
                        }
                    }//if (curWord >= wordIndexesLen)

                    //fstDocList = fstWifq.WordIndex.GetNext();
                    //docListArr[0] = fstDocList;

                    fstWifq.WordIndex.GetNextOriginal(ref fstODPL);
                    fstODPL.ToDocumentPositionList(ref docListArr[0]);
                }
            }

            //Merge score if upDict != null
            if (upDict != null)
            {
                if (!upDict.Not)
                {
                    foreach (int docid in docIdRank.Keys)
                    {
                        DocumentResult *upDrp;

                        if (upDict.TryGetValue(docid, out upDrp))
                        {
                            DocumentResult *drpResult;
                            if (docIdRank.TryGetValue(docid, out drpResult))
                            {
                                drpResult->Score += upDrp->Score;
                            }
                        }
                    }
                }
            }

            DeleteProvider delProvider = _DBProvider.DelProvider;
            int            delCount    = delProvider.Filter(docIdRank);

            if (oneWordOptimize && _QueryParameter.CanLoadPartOfDocs && upDict == null)
            {
                docIdRank.RelTotalCount = wordIndexes[0].RelTotalCount - delCount;
            }
            else
            {
                docIdRank.RelTotalCount = docIdRank.Count;
            }

            performanceReport.Stop();
        }
예제 #7
0
        private unsafe void CalculateNormal(Hubble.Core.SFQL.Parse.DocumentResultWhereDictionary upDict, ref Hubble.Core.SFQL.Parse.DocumentResultWhereDictionary docIdRank)
        {
            DBProvider dBProvider  = Argument.DBProvider;
            bool       needGroupBy = Argument.NeedGroupBy;

            bool           needFilterUntokenizedConditions = this.Argument.NeedFilterUntokenizedConditions;
            ExpressionTree untokenizedTree = this.Argument.UntokenizedTreeOnRoot;

            Query.DocumentResult  documentResult;
            Query.DocumentResult *drp = &documentResult;

            //vars for delete
            bool haveRecordsDeleted = dBProvider.DelProvider.Count > 0;

            int[] delDocs     = null;
            int   curDelIndex = 0;
            int   curDelDocid = 0;

            Field[]            orderByFields;
            DocId2LongComparer comparer = DocId2LongComparer.Generate(
                dBProvider, Argument.OrderBys, out orderByFields);

            if (haveRecordsDeleted)
            {
                delDocs     = dBProvider.DelProvider.DelDocs;
                curDelDocid = delDocs[curDelIndex];
            }


            double ratio = 1;

            WordIndexForQuery[] wordIndexes = WordIndexes;

            if (wordIndexes.Length > 1)
            {
                ratio = (double)2 / (double)(wordIndexes.Length - 1);
            }

            int wordIndexesLen = wordIndexes.Length;

            WordIndexForQuery fstWifq = wordIndexes[0]; //first word

            OriginalDocumentPositionList fstODPL = new OriginalDocumentPositionList();

            //Entity.DocumentPositionList fstDocList = fstWifq.WordIndex.GetNext();

            Entity.DocumentPositionList[] docListArr = new Hubble.Core.Entity.DocumentPositionList[wordIndexesLen];

            //docListArr[0] = fstDocList;
            //fstWifq.WordIndex.GetNextOriginal(ref fstODPL);
            //fstODPL.ToDocumentPositionList(ref docListArr[0]);

            GetNext(fstWifq, ref fstODPL, ref docListArr[0]);

            OriginalDocumentPositionList odpl = new OriginalDocumentPositionList();

            Entity.DocumentPositionList lastDocList
                = new Hubble.Core.Entity.DocumentPositionList();
            int top;

            //calculate top
            //If less than 100, set to 100
            if (this.Argument.End >= 0)
            {
                top = (1 + this.Argument.End / 100) * 100;

                if (top <= 0)
                {
                    top = 100;
                }

                //if (this.Argument.End * 2 > top)
                //{
                //    top *= 2;
                //}
            }
            else
            {
                top = int.MaxValue;
            }

            PriorQueue <Docid2Long> priorQueue = new PriorQueue <Docid2Long>(top, comparer);

            int rows = 0;

            Docid2Long cur  = new Docid2Long();
            Docid2Long last = new Docid2Long();

            last.DocId = -1;

            while (fstODPL.DocumentId >= 0)
            {
                int curWord    = 1;
                int firstDocId = fstODPL.DocumentId;

                while (curWord < wordIndexesLen)
                {
                    //docListArr[curWord] = wordIndexes[curWord].WordIndex.Get(firstDocId);

                    wordIndexes[curWord].WordIndex.GetNextOriginalWithDocId(ref odpl, firstDocId);
                    odpl.ToDocumentPositionList(ref docListArr[curWord]);

                    if (docListArr[curWord].DocumentId < 0)
                    {
                        if ((wordIndexes[curWord].Flags & WordInfo.Flag.Or) != 0)
                        {
                            curWord++;
                            continue;
                        }
                        else
                        {
                            break;
                        }
                    }

                    curWord++;
                } //While

                if (curWord >= wordIndexesLen)
                {
                    //Process untokenized conditions.
                    //If is not matched, get the next one.
                    if (needFilterUntokenizedConditions)
                    {
                        int docId = firstDocId;
                        drp->DocId       = docId;
                        drp->PayloadData = dBProvider.GetPayloadDataWithShareLock(docId);
                        if (!ParseWhere.GetComparisionExpressionValue(dBProvider, drp,
                                                                      untokenizedTree))
                        {
                            GetNext(fstWifq, ref fstODPL, ref docListArr[0]);
                            continue;
                        }
                    }

                    //Matched
                    //Caculate score

                    long totalScore = 0;
                    lastDocList.Count         = 0;
                    lastDocList.FirstPosition = 0;

                    for (int i = 0; i < wordIndexesLen; i++)
                    {
                        WordIndexForQuery wifq = wordIndexes[i];

                        if (wifq.WordIndex.Count == 0)
                        {
                            //a^5000^0 b^5000^2^1
                            //if has a and hasn't b but b can be or
                            //2010-09-30 eaglet
                            continue;
                        }

                        Entity.DocumentPositionList docList = docListArr[i];


                        long score = (long)wifq.FieldRank * (long)wifq.WordRank * (long)wifq.Idf_t * (long)docList.Count * (long)1000000 / ((long)wifq.Sum_d_t * (long)docList.TotalWordsInThisDocument);

                        if (score < 0)
                        {
                            //Overflow
                            score = long.MaxValue - 4000000;
                        }

                        double delta = 1;

                        if (i > 0)
                        {
                            //Calculate with position
                            double queryPositionDelta = wifq.FirstPosition - wordIndexes[i - 1].FirstPosition;
                            double positionDelta      = docList.FirstPosition - lastDocList.FirstPosition;

                            delta = Math.Abs(queryPositionDelta - positionDelta);

                            if (delta < 0.031)
                            {
                                delta = 0.031;
                            }
                            else if (delta <= 1.1)
                            {
                                delta = 0.5;
                            }
                            else if (delta <= 2.1)
                            {
                                delta = 1;
                            }

                            delta = Math.Pow((1 / delta), ratio) * docList.Count * lastDocList.Count /
                                    (double)(wifq.QueryCount * wordIndexes[i - 1].QueryCount);
                        }

                        lastDocList.Count         = docList.Count;
                        lastDocList.FirstPosition = docList.FirstPosition;

                        totalScore += (long)(score * delta);
                    } //End for cycle

                    if (haveRecordsDeleted)
                    {
                        if (curDelIndex < delDocs.Length)
                        {
                            //If docid deleted, get next
                            if (firstDocId == curDelDocid)
                            {
                                GetNext(fstWifq, ref fstODPL, ref docListArr[0]);
                                continue;
                            }
                            else if (firstDocId > curDelDocid)
                            {
                                while (curDelIndex < delDocs.Length && curDelDocid < firstDocId)
                                {
                                    curDelIndex++;

                                    if (curDelIndex >= delDocs.Length)
                                    {
                                        haveRecordsDeleted = false;
                                        break;
                                    }

                                    curDelDocid = delDocs[curDelIndex];
                                }

                                if (curDelIndex < delDocs.Length)
                                {
                                    if (firstDocId == curDelDocid)
                                    {
                                        GetNext(fstWifq, ref fstODPL, ref docListArr[0]);
                                        continue;
                                    }
                                }
                            }
                        }
                    }

                    if (needGroupBy)
                    {
                        docIdRank.AddToGroupByCollection(firstDocId);
                    }

                    if (_HasRankField)
                    {
                        int rank = dBProvider.SharedPayloadProvider.GetPayloadRank(firstDocId);
                        totalScore *= rank;
                        if (totalScore < 0)
                        {
                            totalScore = long.MaxValue - 4000000;
                        }
                    }

                    if (rows >= top)
                    {
                        rows++;

                        cur.DocId = firstDocId;

                        Docid2Long.Generate(ref cur, dBProvider, orderByFields, totalScore);

                        if (comparer.Compare(last, cur) > 0)
                        {
                            priorQueue.Add(cur);
                            last = priorQueue.Last;
                        }
                    }
                    else
                    {
                        cur.DocId = firstDocId;

                        Docid2Long.Generate(ref cur, dBProvider, orderByFields, totalScore);
                        priorQueue.Add(cur);

                        rows++;

                        if (rows == top)
                        {
                            last = priorQueue.Last;
                        }
                    }

                    //docIdRank.Add(firstDocId, totalScore);
                }//if (curWord >= wordIndexesLen)

                GetNext(fstWifq, ref fstODPL, ref docListArr[0]);

                //fstWifq.WordIndex.GetNextOriginal(ref fstODPL);
                //fstODPL.ToDocumentPositionList(ref docListArr[0]);
            }

            docIdRank.RelTotalCount = rows;

            foreach (Docid2Long docid2Long in priorQueue.ToArray())
            {
                long score = comparer.GetScore(docid2Long);

                if (score < 0)
                {
                    //Overflow
                    score = long.MaxValue - 4000000;
                }

                docIdRank.Add(docid2Long.DocId, new DocumentResult(docid2Long.DocId, score));
            }

            docIdRank.Sorted = true;
        }
예제 #8
0
        /// <summary>
        /// order by except only order by score desc.
        /// </summary>
        /// <param name="upDict"></param>
        /// <param name="docIdRank"></param>
        unsafe public void CalculateOptimizeNormalOrderBy(Core.SFQL.Parse.DocumentResultWhereDictionary upDict,
                                                          ref Core.SFQL.Parse.DocumentResultWhereDictionary docIdRank)
        {
            DBProvider dBProvider = Argument.DBProvider;

            Argument.DBProvider.SharedPayloadProvider.EnterPayloladShareLock();

            bool           needFilterUntokenizedConditions = this.Argument.NeedFilterUntokenizedConditions;
            ExpressionTree untokenizedTree = this.Argument.UntokenizedTreeOnRoot;

            Query.DocumentResult  documentResult;
            Query.DocumentResult *drp = &documentResult;

            bool orderByIncludingScore = Argument.OrderByIncludingScore();

            try
            {
                Field[] orderByFields;

                DocId2LongComparer comparer = DocId2LongComparer.Generate(
                    dBProvider, Argument.OrderBys, out orderByFields);

                bool needGroupBy = Argument.NeedGroupBy;

                WordIndexForQuery wifq = WordIndexes[0];
                _IndexReader = wifq.WordIndex.IndexReader;

                Data.Field rankField = Argument.DBProvider.GetField("Rank");

                if (rankField != null)
                {
                    if (rankField.DataType == Hubble.Core.Data.DataType.Int &&
                        rankField.IndexType == Hubble.Core.Data.Field.Index.Untokenized)
                    {
                        _HasRandField         = true;
                        _RankTab              = rankField.TabIndex;
                        _DocidPayloads        = new OriginalDocumentPositionList[2 * 1024];
                        _CurDocidPayloadIndex = _DocidPayloads.Length;
                    }
                }

                if (_IndexReader != null)
                {
                    int top;

                    //vars for delete
                    bool  haveRecordsDeleted = dBProvider.DelProvider.Count > 0;
                    int[] delDocs            = null;
                    int   curDelIndex        = 0;
                    int   curDelDocid        = 0;
                    int   groupByCount       = 0;
                    int   groupByLen         = dBProvider.Table.GroupByLimit;
                    int   groupByStep        = 1;
                    int   groupByIndex       = 0;

                    if (needGroupBy)
                    {
                        groupByStep = wifq.RelTotalCount / groupByLen;

                        if (groupByStep <= 0)
                        {
                            groupByStep = 1;
                        }
                    }

                    if (haveRecordsDeleted)
                    {
                        delDocs     = dBProvider.DelProvider.DelDocs;
                        curDelDocid = delDocs[curDelIndex];
                    }

                    try
                    {
                        //calculate top
                        //If less than 100, set to 100
                        if (this.Argument.End >= 0)
                        {
                            top = (1 + this.Argument.End / 100) * 100;

                            if (top <= 0)
                            {
                                top = 100;
                            }

                            //if (this.Argument.End * 2 > top)
                            //{
                            //    top *= 2;
                            //}
                        }
                        else
                        {
                            top = int.MaxValue;
                        }

                        PriorQueue <Docid2Long> priorQueue = new PriorQueue <Docid2Long>(top, comparer);
                        int rows = 0;

                        Entity.OriginalDocumentPositionList docList = new OriginalDocumentPositionList();

                        bool notEOF = GetNext(ref docList);

                        Index.WordIndexReader wordIndexReader = wifq.WordIndex;

                        Docid2Long last = new Docid2Long();
                        last.DocId = -1;

                        int relCount = 0;

                        while (notEOF)
                        {
                            //Process untokenized conditions.
                            //If is not matched, get the next one.
                            if (needFilterUntokenizedConditions)
                            {
                                int docId = docList.DocumentId;
                                drp->DocId       = docId;
                                drp->PayloadData = dBProvider.GetPayloadDataWithShareLock(docId);
                                if (!ParseWhere.GetComparisionExpressionValue(dBProvider, drp,
                                                                              untokenizedTree))
                                {
                                    notEOF = GetNext(ref docList);
                                    continue;
                                }
                            }

                            //Process deleted records
                            if (haveRecordsDeleted)
                            {
                                if (curDelIndex < delDocs.Length)
                                {
                                    //If docid deleted, get next
                                    if (docList.DocumentId == curDelDocid)
                                    {
                                        notEOF = GetNext(ref docList);
                                        continue;
                                    }
                                    else if (docList.DocumentId > curDelDocid)
                                    {
                                        while (curDelIndex < delDocs.Length && curDelDocid < docList.DocumentId)
                                        {
                                            curDelIndex++;

                                            if (curDelIndex >= delDocs.Length)
                                            {
                                                haveRecordsDeleted = false;
                                                break;
                                            }

                                            curDelDocid = delDocs[curDelIndex];
                                        }

                                        if (curDelIndex < delDocs.Length)
                                        {
                                            if (docList.DocumentId == curDelDocid)
                                            {
                                                notEOF = GetNext(ref docList);
                                                continue;
                                            }
                                        }
                                    }
                                }
                            }

                            if (needGroupBy)
                            {
                                if (groupByCount < groupByLen)
                                {
                                    if (groupByIndex >= groupByStep)
                                    {
                                        groupByIndex = 0;
                                    }

                                    if (groupByIndex == 0)
                                    {
                                        docIdRank.AddToGroupByCollection(docList.DocumentId);
                                        groupByCount++;
                                    }

                                    groupByIndex++;
                                }
                            }

                            relCount++;

                            Docid2Long cur = new Docid2Long();

                            if (rows >= top)
                            {
                                long score = 1;

                                if (orderByIncludingScore)
                                {
                                    int wordCount = docList.CountAndWordCount / 8; //one word, score = count
                                    score = (long)wifq.FieldRank * (long)wifq.WordRank * (long)wifq.Idf_t * (long)wordCount * (long)1000000 /
                                            ((long)wifq.Sum_d_t * (long)docList.TotalWordsInThisDocument);
                                }

                                cur.DocId = docList.DocumentId;
                                cur.Rank  = docList.TotalWordsInThisDocument;

                                Docid2Long.Generate(ref cur, dBProvider, orderByFields, score);

                                if (comparer.Compare(last, cur) > 0)
                                {
                                    priorQueue.Add(cur);
                                    last = priorQueue.Last;
                                }
                            }
                            else
                            {
                                long score = 1;

                                if (orderByIncludingScore)
                                {
                                    int wordCount = docList.CountAndWordCount / 8; //one word, score = count
                                    score = (long)wifq.FieldRank * (long)wifq.WordRank * (long)wifq.Idf_t * (long)wordCount * (long)1000000 /
                                            ((long)wifq.Sum_d_t * (long)docList.TotalWordsInThisDocument);
                                }

                                if (score < 0)
                                {
                                    //Overflow
                                    score = long.MaxValue - 4000000;
                                }

                                cur.DocId = docList.DocumentId;
                                cur.Rank  = docList.TotalWordsInThisDocument;

                                Docid2Long.Generate(ref cur, dBProvider, orderByFields, score);

                                priorQueue.Add(cur);
                                rows++;

                                if (rows == top)
                                {
                                    last = priorQueue.Last;
                                }
                            }

                            notEOF = GetNext(ref docList);
                        }

                        docIdRank.RelTotalCount = relCount;

                        foreach (Docid2Long docid2Long in priorQueue.ToArray())
                        {
                            long score = comparer.GetScore(docid2Long); //use Rank store TotalWordsInThisDocument

                            if (score < 0)
                            {
                                //Overflow
                                score = long.MaxValue - 4000000;
                            }

                            docIdRank.Add(docid2Long.DocId, new DocumentResult(docid2Long.DocId, score));
                        }
                    }
                    finally
                    {
                    }

                    docIdRank.Sorted = true;
                }
            }
            finally
            {
                Argument.DBProvider.SharedPayloadProvider.LeavePayloadShareLock();
            }
        }
예제 #9
0
        /// <summary>
        /// Get next original document position list by DocId.
        /// </summary>
        /// <param name="odpl"></param>
        /// <param name="docId">docid</param>
        /// <returns>if docid not match, return false</returns>
        public bool GetNextOriginalWithDocId(ref OriginalDocumentPositionList odpl, int docId)
        {
            if (_End)
            {
                odpl.DocumentId = -1;
                return(false);
            }

            if (docId < 0)
            {
                throw new StoreException(string.Format("Invalid docid = {0}", docId));
            }

            if (_NextODPL.DocumentId >= 0)
            {
                if (docId == _NextODPL.DocumentId)
                {
                    odpl = _NextODPL;
                    GetNextOriginal(ref _NextODPL);
                    return(true);
                }
                else if (docId < _NextODPL.DocumentId)
                {
                    odpl.DocumentId = -1;
                    return(false);
                }
            }

            if (!GetNextOriginal(ref odpl))
            {
                odpl.DocumentId = -1;
                return(false);
            }

            if (docId < odpl.DocumentId)
            {
                _NextODPL       = odpl;
                odpl.DocumentId = -1;
                return(false);
            }

            if (docId == odpl.DocumentId)
            {
                return(true);
            }

            if (docId > _LastDocIdInCurrentStep)
            {
                Match(docId); //Get the matched step doc index
            }

            GetNextOriginal(ref odpl);

            while (odpl.DocumentId < docId && odpl.DocumentId >= 0)
            {
                GetNextOriginal(ref odpl);
            }

            if (docId == odpl.DocumentId)
            {
                return(true);
            }
            else
            {
                _NextODPL       = odpl;
                odpl.DocumentId = -1;
                return(false);
            }
        }