예제 #1
0
def testPartition():
    """Test partition function"""
    print "Test"
    arr = [4, 3, 2, 1]
    partition(arr, 0, len(arr) - 1)
    pivoted = [1, 3, 2, 4]
    assert isEqual(arr, pivoted)
예제 #2
0
    def note(self):
        '''
        Summary
        ====
        Print chapter7.1 note

        Example
        ====
        >>> Chapter7_1().note()
        '''
        print('chapter7.1 note as follow')
        print('第7章 快速排序')
        print('快速排序是一种排序算法,对包含n个数的输入数组进行排序,最坏情况的运行时间为Θ(n^2)')
        print('虽然这个最坏情况运行时间比较差,但是快速排序通常是用于排序最佳的实用选择,这是因为其平均性能相当好')
        print('快速排序期望的运行时间为Θ(nlgn),且Θ(nlgn)记号中隐含的常数因子很小')
        print('快速排序能够进行就地排序,在虚存坏境中也能很好地工作')
        print('7.1 快速排序的描述')
        print('像合并排序一样,快速排序也是基于分治模式的')
        print(' 1.分解:数组A[p..r]被划分成两个(可能为空的)子数组A[p..q-1]和A[q+1..r]')
        print('  使得A[p..q-1]中的每个元素都小于等于A(q),而且,小于等于A[q+1..r]')
        print('  下标q也在这个划分过程中进行计算')
        print(' 2.解决:通过递归调用快速排序,对子数组A[p..q-1]和A[q+1..r]排序')
        print(' 3.合并:因为这两个子数组是就地排序的(不开辟新的数组),将他们合并不需要任何操作,整个数组A[p..r]已经排好序')
        print('子数组快速排序伪代码')
        print('QUICKSORT(A,p,r)')
        print(' 1. if q < r')
        print(' 2.   q <- PARTITION(A,p,r)')
        print(' 3.       QUICKSORT(A,p,q-1)')
        print(' 3.       QUICKSORT(A,q+1,r)')
        print('排序完整的数组A,调用QUICKSORT(A,0,len(A))即可')
        print('快速排序算法的关键是PARTITION过程,它对子数组A[q..r]进行就地重排')
        print('PARTITION(A,p,r)')
        print(' 1. x <- A[r]')
        print(' 2. i <- p-1')
        print(' 3. for j <- p to r-1')
        print(' 4.  if A[j] <= x')
        print(' 5.      i <- i+1')
        print(' 6.      exchange A[i] <-> A[j]')
        print(' 7. exchange A[i+1] <-> A[r]')
        print(' 8. return i + 1')
        A = [8, 9, 6, 7, 4, 5, 2, 3, 1]
        print('数组A', _deepcopy(A), '的快速排序过程为:', quicksort.quicksort(A))
        A = [13, 19, 9, 5, 12, 8, 7, 4, 11, 2, 6, 21]
        print('练习7.1-1 数组A', _deepcopy(A), '的一步partition过程得到middle索引为:',
              quicksort.partition(A, 0,
                                  len(A) - 1))
        A = [11, 11, 11, 11, 11]
        print('练习7.1-2 数组A', _deepcopy(A), '的一步partition过程得到middle索引为:',
              quicksort.partition(A, 0,
                                  len(A) - 1))
        print('练习7.1-3 就一个长度为n的for循环,且一定会执行,所以时间复杂度为Θ(n),然后用确界的夹逼定义证明')
        print('练习7.1-4 不等号方向改变即可')
예제 #3
0
def quickselect(arr, low, high, k):
    if low < high:
        p = partition(arr, low, high)
        if p < k:
            quickselect(arr, p + 1, high, k)
        elif p > k:
            quickselect(arr, low, p - 1, k)
예제 #4
0
파일: selection.py 프로젝트: gg/algorithms
def randomized_selection(A, i, first=None, last=None):
    '''Returns the `i`th smallest element (indexed from 0) in `A[first:last]`.

    Requires `len(A) > i`.

    `A` must not contain duplicate elements.

    Recursively partitions `A`, as in randomized quicksort, where the pivot is
    chosen uniformly at random.

    >>> randomized_selection([3, 5, 7, 1, 9, 4, 6, 8], 4)
    6
    '''
    first = first if first is not None else 0
    last = last if last is not None else len(A)

    if last - first == 1:
        return A[first]

    pivot_index, _ = quicksort.partition(A, first, last,
                                         quicksort.random_pivot)

    normalized_pivot_index = pivot_index - first

    if normalized_pivot_index == i:
        return A[pivot_index]
    elif normalized_pivot_index > i:
        return randomized_selection(A, i, first, pivot_index)
    else:
        return randomized_selection(A, i - normalized_pivot_index - 1,
                                    pivot_index + 1, last)
예제 #5
0
def test_partition():
    """Test the partition returns a modified list and value we expect."""
    from quicksort import partition
    test_list = [0, 1]
    lo = 0
    hi = len(test_list) - 1
    pivot_point, a_list = partition(test_list, lo, hi)
    assert pivot_point == 1
    assert a_list == [0, 1]
예제 #6
0
def selection(L, p, r, i):
    if p == r:
        return L[p]
    q = partition(L, p, r)
    k = q - p + 1
    if i == k:
        return L[q]
    elif i < k:
        return selection(L, p, q - 1, i)
    else:
        return selection(L, q + 1, r, i - k)
예제 #7
0
def tail_recursive_quicksort(A, p, r):
    while p < r:
        q = partition(A, p, r)
        l_size = q - p
        r_size = r - q
        if l_size < r_size:
            tail_recursive_quicksort(A, p, q - 1)
            p = q + 1  # larger is from A[q+1...r], hence p = q+1
        else:
            tail_recursive_quicksort(A, q + 1, r)
            r = q - 1  # larger is from A[p...q-1], hence r = q-1
def test_partition(seq: list, l_i: int, r_i: int, p_i: int,
                   p_i_expected: int) -> None:
    """Verify partition step works."""
    pivot = seq[p_i]

    seq_actual, p_i_actual = quicksort.partition(seq, l_i, r_i, p_i)

    assert p_i_actual == p_i_expected
    assert seq_actual[p_i_expected] == pivot
    assert all(x < seq_actual[p_i_expected] for x in seq_actual[:p_i_expected])
    assert all(x > seq_actual[p_i_expected]
               for x in seq_actual[p_i_expected + 1:])
예제 #9
0
def order_select(l, p, r, i):
    # no randomization implemented here
    if p == r:
        return l[p]

    index = i - 1
    pivot_index = partition(l, p, r)
    if index == pivot_index:
        return l[pivot_index]

    if index > pivot_index:
        return order_select(l, pivot_index + 1, r, index - pivot_index)
    else:
        return order_select(l, p, pivot_index - 1, i)
def introSort(data, start, end, depth):
    if start < end:
        if depth == 0:
            # Switch from quicksort to heapsort
            heapSort(data, start, end)
            Plot(max(data[start:end + 1]), data)
            return

        # Return the pivot index
        p = partition(data, start, end)

        # Sort all the elements to the left and to the right of the pivot
        introSort(data, start, p - 1, depth - 1)
        introSort(data, p + 1, end, depth - 1)
예제 #11
0
def kthtop(array,k):
    
    shuffle(array)
    
    low = 0
    high = len(array) - 1
    
    while(high > low):
        j = partition(array, low, high)
        if j < k: low = j + 1
        elif j > k: high = j - 1
        else: return array[k]
        
    return array[k]
예제 #12
0
def RSelection(A, low, n, order_statistic):
    if low == n:
        return A[low]
    if order_statistic == 0:
        return -1
    if n > low:
        pivot = random.randrange(low, n + 1)
        pivot_index = quicksort.partition(A, 0, n, pivot)
        i = pivot_index - low + 1
        if i == order_statistic:
            return A[pivot_index]
        elif i > order_statistic:
            return RSelection(A, low, pivot_index - 1, order_statistic)
        else:
            return RSelection(A, pivot_index + 1, n, order_statistic - i)
예제 #13
0
def RSelect(arr, l, r, k):
    if len(arr) == 1:
        return arr[0]
    if l > r:
        i = l
    else:
        i = randint(l, r)
    print(f"i : {i}")
    arr[l], arr[i] = arr[i], arr[l]
    j = partition(arr, l, r)
    if j + 1 == k:
        print(arr)
        return arr[j]
    elif j > k:
        return RSelect(arr, l, j - 1, k)
    else:
        return RSelect(arr, j + 1, r, k)
예제 #14
0
def select_statistic_random(lst, start, end, i):
    """ select i-statistic algorithm use random element everytime """
    if start >= end:
        return lst[start]
    # select random pivot element
    pivot = random.randint(start, end)
    # swap pivot and last element into list
    lst[-1], lst[pivot] = lst[-1], lst[pivot]
    # regrouping the list
    new_pivot = partition(lst, start, end)
    k = new_pivot - start + 1
    if i == k:
        return lst[new_pivot]
    elif i < k:
        # run recursive quick sort for left half
        return select_statistic_random(lst, start, new_pivot - 1, i)
    else:
        # run for right half
        return select_statistic_random(lst, new_pivot + 1, end, i - k)
예제 #15
0
def top(i, array, start=None, end=None):

    try:
        if i > len(array):
            raise UnboundLocalError('Error: ith position greater that the length of the array')

        quicksort.randomize_pivot(array, end, start)

        pivot = quicksort.partition(array, start, end)

        ith_pos = i-1

        if ith_pos == pivot:
            return array[pivot]

        if ith_pos < pivot:
            return top(i, array, 0, pivot-1)
        else:
            return top(i, array, pivot + 1, end)

    except UnboundLocalError as e:
        raise e
예제 #16
0
def select(data, p, r, i):
    """ Selects the ith smallest elements of self.data from p to r. Guarantees a good split by choosing the median
    of medians of blocks of size 5.

    Attributes:

        p -- a starting index
        r -- an end index
        i -- an index of the smallest element
    """
    if p == r:
        return data[p]
    # divide the group of elements into n/5 groups of 5 elements each
    medians = [] # a list of medians from each group
    last = r
    j = p
    while j < last + 1:
        end = j + 5
        if end > last + 1:
            end = last + 1
        insertion_sort(data, j, end)
        mid = (j + end - 1) / 2
        medians.append(data.pop(mid))
        last -= 1
        j += 4
    # put medians at the head of the list
    data[p:p] = medians
    # use select recursively to find the median of medians
    median = select(data, p, p + len(medians) - 1, (len(medians) + 1) / 2)
    data[data.index(median)], data[r] = data[r], data[data.index(median)]
    q = quicksort.partition(data, p, r)
    k = q - p + 1
    if i == k:
        return data[q]
    elif i < k:
        return select(data, p, q - 1, i)
    else:
        return select(data, q + 1, r, i - k)
예제 #17
0
파일: quicksort2.py 프로젝트: not7cd/aisd
def solution(A):
    m = 1
    left = 0
    right = len(A) - 1
    s = [(0, 0)]
    while left < right:
        i, j = partition(A, left, right)
        _jl = j - left
        _ri = right - i
        if _jl < m and _ri < m:
            left, right = s.pop()
        elif _jl < m and _ri >= m:
            left = i
        elif _jl >= m and _ri < m:
            right = j
        elif _jl >= m and _ri >= m:
            if _jl >= _ri:
                s.append((left, j))
                left = i
            else:
                s.append((i, right))
                right = j
    return A
예제 #18
0
 def test_kind_of_unsorted_list_4(self):
     array = [1, 3, 2, 4]
     pivot = partition(array, 2)
     self.assertEqual(pivot, 1)
     self.assertPivot(array, pivot)
예제 #19
0
 def test_sorted_non_contiguous_list(self):
     array = [1, 2, 4]
     pivot = partition(array, 2)
     self.assertEqual(pivot, 2)
     self.assertPivot(array, pivot)
예제 #20
0
 def test_unsorted_list(self):
     array = [3, 1, 2]
     pivot = partition(array, 2)
     self.assertEqual(pivot, 1)
     self.assertPivot(array, pivot)
예제 #21
0
 def test_reversed_list(self):
     array = [3, 2, 1]
     pivot = partition(array, 1)
     self.assertEqual(pivot, 1)
     self.assertPivot(array, pivot)
예제 #22
0
def randomizedpartition(A, p, r):
    i = random.randrange(p, r)   
    quicksort.exchange(A, i, r)
    return quicksort.partition(A, p, r)
예제 #23
0
 def test_rotated_list__5(self):
     array = [4, 1, 5, 2, 3]
     pivot = partition(array, 3)
     self.assertEqual(pivot, 1)
     self.assertPivot(array, pivot)   
예제 #24
0
def randomized_partition(A, p, r):
    i = random.randint(p, r)
    A[i], A[r] = A[r], A[i]
    return partition(A, p, r)
예제 #25
0
    def test_partition(self):
        a = [2, 1, 3]
        q = qs.partition(a, 0, len(a) - 1)

        self.assertEqual(q, 2)
예제 #26
0
def random_partition(arr, left, right):
    p = random.randint(left, right)
    arr[right], arr[p] = arr[p], arr[right]
    mid = partition(arr, left, right)
    return mid
예제 #27
0
def partition_random(A, p, r):
    i = random.randint(p, r)
    A[r], A[i] = A[i], A[r]
    return quicksort.partition(A, p, r)
예제 #28
0
 def test_partition_2(self):
     array = [3, 8, 2, 5, 1, 4, 7, 6]
     self.assertEquals(partition(array, 0, 7), (0, 4, 6, 7))
예제 #29
0
 def test_yet_another_unsorted_list_4(self):
     array = [3, 1, 2, 4]
     pivot = partition(array, 2)
     self.assertEqual(pivot, 1)
     self.assertPivot(array, pivot)
예제 #30
0
def test_partition():
    #     l&i                      r 
    arr = [4, 8, 7, 0, 2, 6, 5, 3, 1]
    i = 0                               # index of pivot element
    l = 0                               # index of starting element
    r = len(arr) - 1                    # index of ending element
    assert i == 0, 'index of pivot element is set to first element'
    assert arr[i] == 4
    i = partition(arr, l, r, i)
    assert i == 4
    assert arr[i] == 4
    assert all(x < 4 for x in arr[l:i])
    assert all(x > 4 for x in arr[i+1:r])

    #      l  i                    r 
    arr = [4, 8, 7, 0, 2, 6, 5, 3, 1]
    i = 1                               # index of pivot element
    l = 0                               # index of starting element
    r = len(arr) - 1                    # index of ending element
    assert i == 1
    assert arr[i] == 8
    i = partition(arr, l, r, i)
    assert i == 8
    assert arr[i] == 8
    assert all(x < 8 for x in arr[l:i])
    assert all(x > 8 for x in arr[i+1:r])

    #      l                      i&r 
    arr = [4, 8, 7, 0, 2, 6, 5, 3, 1]
    i = 8                               # index of pivot element
    l = 0                               # index of starting element
    r = len(arr) - 1                    # index of ending element
    assert i == 8
    assert arr[i] == 1
    i = partition(arr, l, r, i)
    assert i == 1
    assert arr[i] == 1
    assert all(x < 1 for x in arr[l:i])
    assert all(x > 1 for x in arr[i+1:r])

    #            l     i     r
    arr = [4, 8, 7, 0, 2, 6, 5, 3, 1]
        # [      7, 0, 2, 6, 5      ]
        # [      0, 2, 7, 6, 5      ]
        #  0  1  2  3
    i = 4                               # index of pivot element
    l = 2                               # index of starting element
    r = 6                               # index of ending element
    assert i == 4
    assert arr[i] == 2
    i = partition(arr, l, r, i)
    assert i == 3
    assert arr[i] == 2
    assert all(x < 2 for x in arr[l:i])
    assert all(x > 2 for x in arr[i+1:r])

    #    l&i&r
    arr = [1]
    i = 0                               # index of pivot element
    l = 0                               # index of starting element
    r = 0                               # index of ending element
    comparisons = Counter()
    assert i == 0
    assert arr[i] == 1
    i = partition(arr, l, r, i, count=comparisons)
    assert i == 0
    assert arr[i] == 1
    assert comparisons.total == 0
    assert all(x < 1 for x in arr[l:i])
    assert all(x > 1 for x in arr[i+1:r])

    #      l i&r
    arr = [1, 2]
    i = 1                               # index of pivot element
    l = 0                               # index of starting element
    r = 1                               # index of ending element
    comparisons = Counter()
    assert i == 1
    assert arr[i] == 2
    i = partition(arr, l, r, i, count=comparisons)
    assert i == 1
    assert arr[i] == 2
    assert comparisons.total == 1
    assert all(x < 2 for x in arr[l:i])
    assert all(x > 2 for x in arr[i+1:r])

    #     l&i r
    arr = [1, 2]
    i = 0                               # index of pivot element
    l = 0                               # index of starting element
    r = 1                               # index of ending element
    comparisons = Counter()
    assert i == 0
    assert arr[i] == 1
    i = partition(arr, l, r, i, count=comparisons)
    assert i == 0
    assert arr[i] == 1
    assert comparisons.total == 1
    assert all(x < 1 for x in arr[l:i])
    assert all(x > 1 for x in arr[i+1:r])
예제 #31
0
 def test_sorted_list(self):
     array = [1, 2, 3]
     pivot = partition(array, 1)
     self.assertEqual(pivot, 1)
     self.assertPivot(array, pivot)
예제 #32
0
def test_quicksort():
    eq_(quicksort.partition([4, 5, 3, 7, 2]), [3, 2, 4, 5, 7])
예제 #33
0
 def test_partition_1(self):
     array = [3, 5, 1, 4, 2, 6]
     self.assertEquals(partition(array, 0, 5), (0, 4, 6, 5))
예제 #34
0
 def test_partition(self):
     a = [2, 8, 7, 1, 3, 5, 6, 4]
     partition(a, 0, 7)
     self.assertEquals(a, [2, 1, 3, 4, 7, 5, 6, 8])
예제 #35
0
def randomquicksort(A: list, begin: int, end: int):
    if end > begin:
        randomize(A, begin, end)
        compare = quicksort.partition(A, begin, end)
        randomquicksort(A, begin, compare - 1)
        randomquicksort(A, compare + 1, end)
예제 #36
0
 def test_partition_1(self):
     array = [3, 5, 1, 4, 2, 6]
     self.assertEquals(partition(array, 0, 5), (0, 4, 6, 5))
예제 #37
0
def randomised_partition(A, p, r):
    random_index = random.randint(p, r)
    A[r], A[random_index] = A[random_index], A[r]
    return partition(A, p, r)
예제 #38
0
 def test_partition_2(self):
     array = [3, 8, 2, 5, 1, 4, 7, 6]
     self.assertEquals(partition(array, 0, 7), (0, 4, 6, 7))