예제 #1
0
        // Auto-generated variant of sort.go:medianOfThree
        private static void medianOfThree_func(lessSwap data, nint m1, nint m0, nint m2)
        {
            if (data.Less(m1, m0))
            {
                data.Swap(m1, m0);
            }

            if (data.Less(m2, m1))
            {
                data.Swap(m2, m1);
                if (data.Less(m1, m0))
                {
                    data.Swap(m1, m0);
                }
            }
        }
예제 #2
0
 // Auto-generated variant of sort.go:swapRange
 private static void swapRange_func(lessSwap data, nint a, nint b, nint n)
 {
     for (nint i = 0; i < n; i++)
     {
         data.Swap(a + i, b + i);
     }
 }
예제 #3
0
        // Auto-generated variant of sort.go:siftDown
        private static void siftDown_func(lessSwap data, nint lo, nint hi, nint first)
        {
            var root = lo;

            while (true)
            {
                nint child = 2 * root + 1;
                if (child >= hi)
                {
                    break;
                }

                if (child + 1 < hi && data.Less(first + child, first + child + 1))
                {
                    child++;
                }

                if (!data.Less(first + root, first + child))
                {
                    return;
                }

                data.Swap(first + root, first + child);
                root = child;
            }
        }
예제 #4
0
        // Auto-generated variant of sort.go:heapSort
        private static void heapSort_func(lessSwap data, long a, long b)
        {
            var  first = a;
            long lo    = 0L;
            var  hi    = b - a;
            {
                var i__prev1 = i;

                for (var i = (hi - 1L) / 2L; i >= 0L; i--)
                {
                    siftDown_func(data, i, hi, first);
                }


                i = i__prev1;
            }
            {
                var i__prev1 = i;

                for (i = hi - 1L; i >= 0L; i--)
                {
                    data.Swap(first, first + i);
                    siftDown_func(data, lo, i, first);
                }


                i = i__prev1;
            }
        }
예제 #5
0
        // Auto-generated variant of sort.go:siftDown
        private static void siftDown_func(lessSwap data, long lo, long hi, long first)
        {
            var root = lo;

            while (true)
            {
                long child = 2L * root + 1L;
                if (child >= hi)
                {
                    break;
                }

                if (child + 1L < hi && data.Less(first + child, first + child + 1L))
                {
                    child++;
                }

                if (!data.Less(first + root, first + child))
                {
                    return;
                }

                data.Swap(first + root, first + child);
                root = child;
            }
        }
예제 #6
0
 // Auto-generated variant of sort.go:swapRange
 private static void swapRange_func(lessSwap data, long a, long b, long n)
 {
     for (long i = 0L; i < n; i++)
     {
         data.Swap(a + i, b + i);
     }
 }
예제 #7
0
 // Auto-generated variant of sort.go:insertionSort
 private static void insertionSort_func(lessSwap data, nint a, nint b)
 {
     for (var i = a + 1; i < b; i++)
     {
         for (var j = i; j > a && data.Less(j, j - 1); j--)
         {
             data.Swap(j, j - 1);
         }
     }
 }
예제 #8
0
        // Auto-generated variant of sort.go:heapSort
        private static void heapSort_func(lessSwap data, nint a, nint b)
        {
            var  first = a;
            nint lo    = 0;
            var  hi    = b - a;

            for (var i = (hi - 1) / 2; i >= 0; i--)
            {
                siftDown_func(data, i, hi, first);
            }

            for (var i = hi - 1; i >= 0; i--)
            {
                data.Swap(first, first + i);
                siftDown_func(data, lo, i, first);
            }
        }
예제 #9
0
        // Auto-generated variant of sort.go:quickSort
        private static void quickSort_func(lessSwap data, nint a, nint b, nint maxDepth)
        {
            while (b - a > 12)
            {
                if (maxDepth == 0)
                {
                    heapSort_func(data, a, b);
                    return;
                }

                maxDepth--;
                var(mlo, mhi) = doPivot_func(data, a, b);
                if (mlo - a < b - mhi)
                {
                    quickSort_func(data, a, mlo, maxDepth);
                    a = mhi;
                }
                else
                {
                    quickSort_func(data, mhi, b, maxDepth);
                    b = mlo;
                }
            }

            if (b - a > 1)
            {
                for (var i = a + 6; i < b; i++)
                {
                    if (data.Less(i, i - 6))
                    {
                        data.Swap(i, i - 6);
                    }
                }

                insertionSort_func(data, a, b);
            }
        }
예제 #10
0
        // Auto-generated variant of sort.go:symMerge
        private static void symMerge_func(lessSwap data, nint a, nint m, nint b)
        {
            if (m - a == 1)
            {
                var i = m;
                var j = b;
                while (i < j)
                {
                    var h = (nint)((nuint)(i + j) >> 1);
                    if (data.Less(h, a))
                    {
                        i = h + 1;
                    }
                    else
                    {
                        j = h;
                    }
                }

                for (var k = a; k < i - 1; k++)
                {
                    data.Swap(k, k + 1);
                }

                return;
            }

            if (b - m == 1)
            {
                var i = a;
                var j = m;
                while (i < j)
                {
                    var h = (nint)((nuint)(i + j) >> 1);
                    if (!data.Less(m, h))
                    {
                        i = h + 1;
                    }
                    else
                    {
                        j = h;
                    }
                }

                for (var k = m; k > i; k--)
                {
                    data.Swap(k, k - 1);
                }

                return;
            }

            var  mid = (nint)((nuint)(a + b) >> 1);
            var  n = mid + m;
            nint start = default;            nint r = default;

            if (m > mid)
            {
                start = n - b;
                r     = mid;
            }
            else
            {
                start = a;
                r     = m;
            }

            var p = n - 1;

            while (start < r)
            {
                var c = (nint)((nuint)(start + r) >> 1);
                if (!data.Less(p - c, c))
                {
                    start = c + 1;
                }
                else
                {
                    r = c;
                }
            }

            var end = n - start;

            if (start < m && m < end)
            {
                rotate_func(data, start, m, end);
            }

            if (a < start && start < mid)
            {
                symMerge_func(data, a, start, mid);
            }

            if (mid < end && end < b)
            {
                symMerge_func(data, mid, end, b);
            }
        }
예제 #11
0
        // Auto-generated variant of sort.go:doPivot
        private static (nint, nint) doPivot_func(lessSwap data, nint lo, nint hi)
        {
            nint midlo = default;
            nint midhi = default;

            var m = (nint)((nuint)(lo + hi) >> 1);

            if (hi - lo > 40)
            {
                var s = (hi - lo) / 8;
                medianOfThree_func(data, lo, lo + s, lo + 2 * s);
                medianOfThree_func(data, m, m - s, m + s);
                medianOfThree_func(data, hi - 1, hi - 1 - s, hi - 1 - 2 * s);
            }

            medianOfThree_func(data, lo, m, hi - 1);
            var pivot = lo;
            var a     = lo + 1;
            var c     = hi - 1;

            while (a < c && data.Less(a, pivot))
            {
                a++;
            }

            var b = a;

            while (true)
            {
                while (b < c && !data.Less(pivot, b))
                {
                    b++;
                }

                while (b < c && data.Less(pivot, c - 1))
                {
                    c--;
                }

                if (b >= c)
                {
                    break;
                }

                data.Swap(b, c - 1);
                b++;
                c--;
            }

            var protect = hi - c < 5L;

            if (!protect && hi - c < (hi - lo) / 4)
            {
                nint dups = 0;
                if (!data.Less(pivot, hi - 1))
                {
                    data.Swap(c, hi - 1);
                    c++;
                    dups++;
                }

                if (!data.Less(b - 1, pivot))
                {
                    b--;
                    dups++;
                }

                if (!data.Less(m, pivot))
                {
                    data.Swap(m, b - 1);
                    b--;
                    dups++;
                }

                protect = dups > 1;
            }

            if (protect)
            {
                while (true)
                {
                    while (a < b && !data.Less(b - 1, pivot))
                    {
                        b--;
                    }

                    while (a < b && data.Less(a, pivot))
                    {
                        a++;
                    }

                    if (a >= b)
                    {
                        break;
                    }

                    data.Swap(a, b - 1);
                    a++;
                    b--;
                }
            }

            data.Swap(pivot, b - 1);
            return(b - 1, c);
        }
예제 #12
0
        // Auto-generated variant of sort.go:symMerge
        private static void symMerge_func(lessSwap data, long a, long m, long b)
        {
            if (m - a == 1L)
            {
                var i = m;
                var j = b;
                while (i < j)
                {
                    var h = int(uint(i + j) >> (int)(1L));
                    if (data.Less(h, a))
                    {
                        i = h + 1L;
                    }
                    else
                    {
                        j = h;
                    }
                }

                {
                    var k__prev1 = k;

                    for (var k = a; k < i - 1L; k++)
                    {
                        data.Swap(k, k + 1L);
                    }


                    k = k__prev1;
                }
                return;
            }

            if (b - m == 1L)
            {
                i = a;
                j = m;
                while (i < j)
                {
                    h = int(uint(i + j) >> (int)(1L));
                    if (!data.Less(m, h))
                    {
                        i = h + 1L;
                    }
                    else
                    {
                        j = h;
                    }
                }

                {
                    var k__prev1 = k;

                    for (k = m; k > i; k--)
                    {
                        data.Swap(k, k - 1L);
                    }


                    k = k__prev1;
                }
                return;
            }

            var  mid = int(uint(a + b) >> (int)(1L));
            var  n = mid + m;
            long start = default;            long r = default;

            if (m > mid)
            {
                start = n - b;
                r     = mid;
            }
            else
            {
                start = a;
                r     = m;
            }

            var p = n - 1L;

            while (start < r)
            {
                var c = int(uint(start + r) >> (int)(1L));
                if (!data.Less(p - c, c))
                {
                    start = c + 1L;
                }
                else
                {
                    r = c;
                }
            }

            var end = n - start;

            if (start < m && m < end)
            {
                rotate_func(data, start, m, end);
            }

            if (a < start && start < mid)
            {
                symMerge_func(data, a, start, mid);
            }

            if (mid < end && end < b)
            {
                symMerge_func(data, mid, end, b);
            }
        }
예제 #13
0
        // Auto-generated variant of sort.go:doPivot
        private static (long, long) doPivot_func(lessSwap data, long lo, long hi)
        {
            long midlo = default;
            long midhi = default;

            var m = int(uint(lo + hi) >> (int)(1L));

            if (hi - lo > 40L)
            {
                var s = (hi - lo) / 8L;
                medianOfThree_func(data, lo, lo + s, lo + 2L * s);
                medianOfThree_func(data, m, m - s, m + s);
                medianOfThree_func(data, hi - 1L, hi - 1L - s, hi - 1L - 2L * s);
            }

            medianOfThree_func(data, lo, m, hi - 1L);
            var pivot = lo;
            var a     = lo + 1L;
            var c     = hi - 1L;

            while (a < c && data.Less(a, pivot))
            {
                a++;
            }

            var b = a;

            while (true)
            {
                while (b < c && !data.Less(pivot, b))
                {
                    b++;
                }

                while (b < c && data.Less(pivot, c - 1L))
                {
                    c--;
                }

                if (b >= c)
                {
                    break;
                }

                data.Swap(b, c - 1L);
                b++;
                c--;
            }

            var protect = hi - c < 5L;

            if (!protect && hi - c < (hi - lo) / 4L)
            {
                long dups = 0L;
                if (!data.Less(pivot, hi - 1L))
                {
                    data.Swap(c, hi - 1L);
                    c++;
                    dups++;
                }

                if (!data.Less(b - 1L, pivot))
                {
                    b--;
                    dups++;
                }

                if (!data.Less(m, pivot))
                {
                    data.Swap(m, b - 1L);
                    b--;
                    dups++;
                }

                protect = dups > 1L;
            }

            if (protect)
            {
                while (true)
                {
                    while (a < b && !data.Less(b - 1L, pivot))
                    {
                        b--;
                    }

                    while (a < b && data.Less(a, pivot))
                    {
                        a++;
                    }

                    if (a >= b)
                    {
                        break;
                    }

                    data.Swap(a, b - 1L);
                    a++;
                    b--;
                }
            }

            data.Swap(pivot, b - 1L);
            return(b - 1L, c);
        }