示例#1
0
        /// <summary>
        /// Finds the range of matches that are greater or equal than low value and lesser or equal to
        /// high value within the sorted sequence by means of a binary search.
        /// Example:
        /// <![CDATA[
        /// int arr = { 1, 1, 2, 5, 5, 5, 8, 8, 10, 12, 12 };
        /// IndexRangeWindow res = FindRange(3, 7);
        /// //res: [low:3 high:7 count:5]
        /// ]]>
        /// </summary>
        /// <param name="lowValue">The low value to search (the highest in the sequence,
        /// if sequence is reversed sort as set in constructor, this will be the higher value).</param>
        /// <param name="highValue">A value higher (further on) in the sequence.</param>
        /// <param name="index">The index at which to begin the search (0 by default).</param>
        /// <param name="length">The length of items to search after index (by default is set to the
        /// sequence length which was set in the Init or constructor).</param>
        public IndexRangeWindow FindRange(T lowValue, T highValue, int index = 0, int?length = null)
        {
            int low  = index;
            int high = _GetHighFromInputLength(low, length);

            // --- both methods below do low,high bounds check so don't do here again ---

            // is low value already greater than high?
            if (compareTo(lowValue, highValue) > 0)
            {
                return(IndexRangeWindow.NoneFound);
            }

            // GET LOW
            int lowRangeIndex = FindLowRange(lowValue, low, high);

            if (lowRangeIndex > high || lowRangeIndex < 0)
            {
                return(IndexRangeWindow.NoneFound);
            }

            // GET HIGH
            int highRangeIndex = FindHighRange(highValue, lowRangeIndex, high);

            var range = new IndexRangeWindow(lowRangeIndex, highRangeIndex);

            return(range);
        }
        /// <summary>
        /// Finds the range of matches of a single value within the sorted sequence
        /// by means of a binary search, see BinarySearch[T].FindSingleRange for further details.
        /// </summary>
        public static IndexRangeWindow BinarySearchFindRange <T>(IList <T> arr, T value,
                                                                 bool reverse = false, int index = 0, int?length = null, Func <T, T, int> comparer = null)
        {
            var bs = new BinarySearch <T>(arr, reverse, comparer);
            IndexRangeWindow result = bs.FindSingleRange(value, index, length);

            return(result);
        }
示例#3
0
        public IndexRangeWindow FindSingleRangeFromFoundLinear(T value, int foundIdx, int index = 0, int?count = null)
        {        //FindSingleRangeFromFoundLinear
            if (foundIdx < 0)
            {
                return(IndexRangeWindow.NoneFound);
            }
            //	BinaryRange r = new BinaryRange(foundIdx, foundIdx);
            //	if(!r.Any)
            //		return r;

            int low  = foundIdx;
            int high = foundIdx;

            for (int i = foundIdx - 1; i >= index; i--)
            {
                T item = _getItemAt(i);
                if (compareTo(value, item) == 0)
                {
                    --low;                     // --r.Low;
                }
                else
                {
                    break;
                }
            }

            int sequenceLength = count ?? _collLength;

            for (int i = foundIdx + 1; i < sequenceLength; i++)
            {
                T item = _getItemAt(i);
                if (compareTo(value, item) == 0)
                {
                    ++high;                     //++r.High;
                }
                else
                {
                    break;
                }
            }
            var result = new IndexRangeWindow(low, high);

            return(result);
        }
示例#4
0
        /// <summary>
        /// Finds the range of matches of a single value within the sorted sequence
        /// by means of a binary search, see overload for further details.
        /// </summary>
        /// <param name="value">Value to search for. Both a FindLowRange and
        /// FindHighRange search will be performed on it.</param>
        /// <param name="index">Index</param>
        /// <param name="length">Count from Index to search on</param>
        public IndexRangeWindow FindSingleRange(T value, int index = 0, int?length = null)
        {
            int low  = index;
            int high = length == null
                                ? _collLength - index - 1
                                : (index + (int)length) - 1;

            // GET LOW
            int lowRangeIndex = FindLowRange(value, low, high);

            if (lowRangeIndex > high || lowRangeIndex < 0)
            {
                return(IndexRangeWindow.NoneFound);
            }

            // GET HIGH
            int highRangeIndex = FindHighRange(value, lowRangeIndex, high);

            var range = new IndexRangeWindow(lowRangeIndex, highRangeIndex);

            return(range);
        }