예제 #1
0
        /// <seealso cref="Array.Copy(Array, Array, int)"/>
        internal static void Copy <T>(SegmentedArray <T> sourceArray, SegmentedArray <T> destinationArray, int length)
        {
            if (length == 0)
            {
                return;
            }

            if (length < 0)
            {
                throw new ArgumentOutOfRangeException(nameof(length));
            }
            if (length > sourceArray.Length)
            {
                throw new ArgumentException(SR.Arg_LongerThanSrcArray, nameof(sourceArray));
            }
            if (length > destinationArray.Length)
            {
                throw new ArgumentException(SR.Arg_LongerThanDestArray, nameof(destinationArray));
            }

            foreach (var(first, second) in GetSegments(sourceArray, destinationArray, length))
            {
                first.CopyTo(second);
            }
        }
예제 #2
0
        public static void Copy <T>(SegmentedArray <T> sourceArray, int sourceIndex, SegmentedArray <T> destinationArray, int destinationIndex, int length)
        {
            if (length < 0)
            {
                throw new ArgumentOutOfRangeException(nameof(length), SR.ArgumentOutOfRange_NeedNonNegNum);
            }
            if (sourceIndex < 0)
            {
                throw new ArgumentOutOfRangeException(nameof(sourceIndex), SR.ArgumentOutOfRange_ArrayLB);
            }
            if (destinationIndex < 0)
            {
                throw new ArgumentOutOfRangeException(nameof(destinationIndex), SR.ArgumentOutOfRange_ArrayLB);
            }
            if ((uint)(sourceIndex + length) > sourceArray.Length)
            {
                throw new ArgumentException(SR.Arg_LongerThanSrcArray, nameof(sourceArray));
            }
            if ((uint)(destinationIndex + length) > destinationArray.Length)
            {
                throw new ArgumentException(SR.Arg_LongerThanDestArray, nameof(destinationArray));
            }

            if (length == 0)
            {
                return;
            }

            foreach (var(first, second) in GetSegmentsUnaligned(sourceArray, sourceIndex, destinationArray, destinationIndex, length))
            {
                first.CopyTo(second);
            }
        }
예제 #3
0
        public static void Reverse <T>(SegmentedArray <T> array, int index, int length)
        {
            if (index < 0)
            {
                ThrowHelper.ThrowIndexArgumentOutOfRange_NeedNonNegNumException();
            }
            if (length < 0)
            {
                ThrowHelper.ThrowLengthArgumentOutOfRange_ArgumentOutOfRange_NeedNonNegNum();
            }
            if (array.Length - index < length)
            {
                ThrowHelper.ThrowArgumentException(ExceptionResource.Argument_InvalidOffLen);
            }

            if (length <= 1)
            {
                return;
            }

            var firstIndex = index;
            var lastIndex  = index + length - 1;

            do
            {
                var temp = array[firstIndex];
                array[firstIndex] = array[lastIndex];
                array[lastIndex]  = temp;
                firstIndex++;
                lastIndex--;
            } while (firstIndex < lastIndex);
        }
예제 #4
0
        public static int IndexOf <T>(SegmentedArray <T> array, T value, int startIndex, int count)
        {
            if ((uint)startIndex > (uint)array.Length)
            {
                ThrowHelper.ThrowStartIndexArgumentOutOfRange_ArgumentOutOfRange_Index();
            }

            if ((uint)count > (uint)(array.Length - startIndex))
            {
                ThrowHelper.ThrowCountArgumentOutOfRange_ArgumentOutOfRange_Count();
            }

            var offset = startIndex;

            foreach (var memory in array.GetSegments(startIndex, count))
            {
                if (!MemoryMarshal.TryGetArray <T>(memory, out var segment))
                {
                    throw new NotSupportedException();
                }

                var index = Array.IndexOf(segment.Array !, value, segment.Offset, segment.Count);
                if (index >= 0)
                {
                    return(index + offset - segment.Offset);
                }

                offset += segment.Count;
            }

            return(-1);
        }
예제 #5
0
 /// <seealso cref="Array.Clear(Array, int, int)"/>
 internal static void Clear <T>(SegmentedArray <T> array, int index, int length)
 {
     foreach (var memory in array.GetSegments(index, length))
     {
         memory.Span.Clear();
     }
 }
예제 #6
0
 public static void Sort <T>(SegmentedArray <T> array)
 {
     if (array.Length > 1)
     {
         var segment = new SegmentedArraySegment <T>(array, 0, array.Length);
         SegmentedArraySortHelper <T> .Sort(segment, (IComparer <T>?) null);
     }
 }
예제 #7
0
        public static void Sort <T>(SegmentedArray <T> array, Comparison <T> comparison)
        {
            if (comparison is null)
            {
                ThrowHelper.ThrowArgumentNullException(ExceptionArgument.comparison);
            }

            if (array.Length > 1)
            {
                var segment = new SegmentedArraySegment <T>(array, 0, array.Length);
                SegmentedArraySortHelper <T> .Sort(segment, comparison);
            }
        }
예제 #8
0
        public static void Copy <T>(SegmentedArray <T> sourceArray, int sourceIndex, Array destinationArray, int destinationIndex, int length)
        {
            if (destinationArray == null)
            {
                ThrowHelper.ThrowArgumentNullException(ExceptionArgument.destinationArray);
            }

            if (typeof(T[]) != destinationArray.GetType() && destinationArray.Rank != 1)
            {
                throw new RankException(SR.Rank_MustMatch);
            }

            if (length < 0)
            {
                throw new ArgumentOutOfRangeException(nameof(length), SR.ArgumentOutOfRange_NeedNonNegNum);
            }
            if (sourceIndex < 0)
            {
                throw new ArgumentOutOfRangeException(nameof(sourceIndex), SR.ArgumentOutOfRange_ArrayLB);
            }

            var dstLB = destinationArray.GetLowerBound(0);

            if (destinationIndex < dstLB || destinationIndex - dstLB < 0)
            {
                throw new ArgumentOutOfRangeException(nameof(destinationIndex), SR.ArgumentOutOfRange_ArrayLB);
            }
            destinationIndex -= dstLB;

            if ((uint)(sourceIndex + length) > sourceArray.Length)
            {
                throw new ArgumentException(SR.Arg_LongerThanSrcArray, nameof(sourceArray));
            }
            if ((uint)(destinationIndex + length) > (nuint)destinationArray.LongLength)
            {
                throw new ArgumentException(SR.Arg_LongerThanDestArray, nameof(destinationArray));
            }

            var copied = 0;

            foreach (var memory in sourceArray.GetSegments(0, length))
            {
                if (!MemoryMarshal.TryGetArray <T>(memory, out var segment))
                {
                    throw new NotSupportedException();
                }

                Array.Copy(segment.Array !, sourceIndex: segment.Offset, destinationArray: destinationArray, destinationIndex: copied, length: segment.Count);
                copied += segment.Count;
            }
        }
예제 #9
0
        public static int BinarySearch <T>(SegmentedArray <T> array, int index, int length, T value, IComparer <T>?comparer)
        {
            if (index < 0)
            {
                ThrowHelper.ThrowIndexArgumentOutOfRange_NeedNonNegNumException();
            }
            if (length < 0)
            {
                ThrowHelper.ThrowLengthArgumentOutOfRange_ArgumentOutOfRange_NeedNonNegNum();
            }
            if (array.Length - index < length)
            {
                ThrowHelper.ThrowArgumentException(ExceptionResource.Argument_InvalidOffLen);
            }

            return(SegmentedArraySortHelper <T> .BinarySearch(array, index, length, value, comparer));
        }
예제 #10
0
        public static int LastIndexOf <T>(SegmentedArray <T> array, T value, int startIndex, int count)
        {
            if (array.Length == 0)
            {
                // Special case for 0 length List
                // accept -1 and 0 as valid startIndex for compatibility reason.
                if (startIndex != -1 && startIndex != 0)
                {
                    ThrowHelper.ThrowStartIndexArgumentOutOfRange_ArgumentOutOfRange_Index();
                }

                // only 0 is a valid value for count if array is empty
                if (count != 0)
                {
                    ThrowHelper.ThrowCountArgumentOutOfRange_ArgumentOutOfRange_Count();
                }

                return(-1);
            }

            // Make sure we're not out of range
            if ((uint)startIndex >= (uint)array.Length)
            {
                ThrowHelper.ThrowStartIndexArgumentOutOfRange_ArgumentOutOfRange_Index();
            }

            // 2nd half of this also catches when startIndex == MAXINT, so MAXINT - 0 + 1 == -1, which is < 0.
            if (count < 0 || startIndex - count + 1 < 0)
            {
                ThrowHelper.ThrowCountArgumentOutOfRange_ArgumentOutOfRange_Count();
            }

            var endIndex = startIndex - count + 1;

            for (var i = startIndex; i >= endIndex; i--)
            {
                if (EqualityComparer <T> .Default.Equals(array[i], value))
                {
                    return(i);
                }
            }

            return(-1);
        }
예제 #11
0
        public static void Sort <T>(SegmentedArray <T> array, int index, int length, IComparer <T>?comparer)
        {
            if (index < 0)
            {
                ThrowHelper.ThrowIndexArgumentOutOfRange_NeedNonNegNumException();
            }
            if (length < 0)
            {
                ThrowHelper.ThrowLengthArgumentOutOfRange_ArgumentOutOfRange_NeedNonNegNum();
            }
            if (array.Length - index < length)
            {
                ThrowHelper.ThrowArgumentException(ExceptionResource.Argument_InvalidOffLen);
            }

            if (length > 1)
            {
                var segment = new SegmentedArraySegment <T>(array, index, length);
                SegmentedArraySortHelper <T> .Sort(segment, comparer);
            }
        }
예제 #12
0
        public static void Copy <T>(SegmentedArray <T> sourceArray, Array destinationArray, int length)
        {
            if (destinationArray is null)
            {
                ThrowHelper.ThrowArgumentNullException(ExceptionArgument.destinationArray);
            }
            if (length == 0)
            {
                return;
            }

            if (length < 0)
            {
                throw new ArgumentOutOfRangeException(nameof(length));
            }
            if (length > sourceArray.Length)
            {
                throw new ArgumentException(SR.Arg_LongerThanSrcArray, nameof(sourceArray));
            }
            if (length > destinationArray.Length)
            {
                throw new ArgumentException(SR.Arg_LongerThanDestArray, nameof(destinationArray));
            }

            var copied = 0;

            foreach (var memory in sourceArray.GetSegments(0, length))
            {
                if (!MemoryMarshal.TryGetArray <T>(memory, out var segment))
                {
                    throw new NotSupportedException();
                }

                Array.Copy(segment.Array !, sourceIndex: segment.Offset, destinationArray: destinationArray, destinationIndex: copied, length: segment.Count);
                copied += segment.Count;
            }
        }
예제 #13
0
 public static void Sort <T>(SegmentedArray <T> array, int index, int length)
 {
     Sort(array, index, length, comparer: null);
 }
예제 #14
0
 public static void Sort <T>(SegmentedArray <T> array, IComparer <T>?comparer)
 {
     Sort(array, 0, array.Length, comparer);
 }
예제 #15
0
 public static int BinarySearch <T>(SegmentedArray <T> array, T value, IComparer <T>?comparer)
 {
     return(BinarySearch(array, 0, array.Length, value, comparer));
 }
예제 #16
0
 public static int BinarySearch <T>(SegmentedArray <T> array, int index, int length, T value)
 {
     return(BinarySearch(array, index, length, value, comparer: null));
 }
예제 #17
0
 public static void Reverse <T>(SegmentedArray <T> array)
 {
     Reverse(array, 0, array.Length);
 }
예제 #18
0
 public static int IndexOf <T>(SegmentedArray <T> array, T value, int startIndex)
 {
     return(IndexOf(array, value, startIndex, array.Length - startIndex));
 }
예제 #19
0
 public static int IndexOf <T>(SegmentedArray <T> array, T value) =>
 IndexOf(array, value, 0, array.Length);
예제 #20
0
 private static SegmentEnumerable <T> GetSegments <T>(this SegmentedArray <T> array, int offset, int length)
 => new(array, offset, length);
예제 #21
0
 public static int LastIndexOf <T>(SegmentedArray <T> array, T value)
 {
     return(LastIndexOf(array, value, array.Length - 1, array.Length));
 }
예제 #22
0
 public static int LastIndexOf <T>(SegmentedArray <T> array, T value, int startIndex)
 {
     return(LastIndexOf(array, value, startIndex, array.Length == 0 ? 0 : startIndex + 1));
 }
예제 #23
0
 public static int BinarySearch <T>(SegmentedArray <T> array, T value) =>
 BinarySearch(array, 0, array.Length, value, comparer: null);