Python data structure implementation (c)

A: sorting algorithm

Merge sort

The basic idea of ​​merge sort:
\qquad Merge sort process can be seen as a divide-and-conquer, first column and the like to be sorted into two halves, each half again merge sort continue (recursion, the sequence of aliquots until only one end of each sequence when the recursive element), and finally every two ordered sequences obtained can merge into a

Merge sort of performance analysis:
time complexity:

  • Run times for sorting logN, per trip basic operations to be done n times (each element in each sequence operation target), then the total number of operations is n * logn, compared with the time complexity O (nlogn)

Space complexity:

  • Uses an auxiliary array, and a length consistent with the length of the column to be sorted, so the space complexity is O (n)
def mergeSort(arr, low, high):
    if low < high:
        mid = (low + high) // 2
        mergeSort(arr, low, mid)
        mergeSort(arr, mid+1, high)
        merge(arr, low, mid, high)

helper = [None] * len(arr)     # 与整个待排序列等长的辅助数组helper
def merge(arr, low, mid, high):
    n = low; i = low; j = mid+1
    for k in range(low,high+1):
        helper[k] = arr[k]
       
    while i < mid+1 and j < high+1:
        if(helper[i] < helper[j]):
            arr[n] = helper[i]
            i += 1
        else:
            arr[n] = helper[j]
            j += 1
        n += 1
        
    # 将剩下的未归并的序列元素依次放入辅助数组中(两个while循环只会执行其中一个)
    while i < mid+1:
        arr[n] = helper[i]
        i += 1; n += 1
    while j < high+1:
        arr[n] = helper[j]
        j += 1; n += 1

Quick Sort

The basic idea of ​​the sort of fast:
\qquad By ordering the trip data to be sorted according to the value of the pivot into separate two parts, than the pivot value is small, a large value of the other part than the pivot axis, and then the two parts of the data in this way were then rapidly sorting, sorting the entire process can be recursively, in order to achieve the whole data into an ordered sequence.

  • The closer the initial sequence order, the lower the quick sort algorithm efficiency;
  • The pivot region when the value of the element is divided into 0 and n-1 elements, the minimum efficiency;

time complexity:

  • Best case: O (logn)
  • Worst case: O (n ^ 2) (to be ordered has been sorted column)

Space complexity:

  • Recursion uses stack space complexity is O (logn)
from random import randint
def quickSort(arr, low, high):
    '''
    这里取arr[low]到arr[high]的任意一个值作为枢轴值pivot作为对快速排序的改进
    (减少区域被划分为0个元素和n-1个元素的几率)
    '''
    i = low; j = high
    if low < high:
        pivotPos = randint(low, high)
        pivot = arr[pivotPos]
        arr[low], arr[pivotPos] = arr[pivotPos], arr[low]     # 将枢轴值放到下标low处
        while i < j:
            while i < j and arr[j] > pivot:
                j -= 1
            if i < j:             # 每次交换前,判断该轮是否其实已经结束
                arr[i] = arr[j]
                i += 1

            while i < j and arr[i] < pivot:   
                i += 1
            if i < j:
                arr[j] = arr[i]
                j -= 1
                
        arr[i] = pivot
        quickSort(arr, low, i-1)
        quickSort(arr, i+1, high)

Insertion Sort

Direct insertion sort

Directly into the basic idea of ​​the sort:
\qquad Each trip to a key to be sorted according to the size of its inserted column values ​​had been properly arranged to the front in the ordered sequence, until all the columns are to be sorted key is inserted into the ordered sequence

time complexity:

  • The worst case: the entire reverse sequence, each time the insertion, the total number of executions is 1 + 2 + ... + n-1 = (n-1) * n / 2, the time complexity is O (n ^ 2)
  • Best case: the entire sequence of ordered, do not need to be inserted each time, the time complexity is O (n)

Space complexity: O (1)

def DinsertSort(arr):
    # 直接插入排序算法
    length = len(arr)
    for i in range(1, length):
        j = i - 1
        temp = arr[i]
        while j>=0 and arr[j]>temp:
            arr[j+1] = arr[j]
            j -= 1
        arr[j+1] = temp
        

Binary insertion sort

The basic idea of ​​binary insertion sort:
\qquad Sorted directly into actually improved, but to find the insertion position of the ordered sequence of binary search method to

time complexity:

  • The worst case: the entire reverse sequence, each time the insertion, the total number of executions is 1 + 2 + ... + n-1 = (n-1) * n / 2, the time complexity is O (n ^ 2)
  • Best case: the whole sequence of ordered, you do not need to be inserted each time (but always look for a logn time), the time complexity is O (nlogn)

Space complexity: O (1)

def Bsearch(arr, low, high, k):
    # 二分查找法
    while low <= high:
        mid = (low + high) // 2
        if arr[mid] == k:
            return mid
        elif arr[mid] < k:
            low = mid + 1
        else:
            high = mid - 1
    return high + 1
            
def BinsertSort(arr):
    length = len(arr)
    for i in range(1,length):
        temp = arr[i]
        insertPos = Bsearch(arr, 0, i-1, temp)
        for j in range(i-1, insertPos-1, -1):
            arr[j+1] = arr[j]
        arr[insertPos] = temp

Bubble Sort

Bubble Sort basic idea:
\qquad Pairwise comparison of two numbers from the beginning of the trip sequentially connected together, a large number of transducers to a post, the first end of the trip switch to the maximum final sequence; similarly for the second pass sorting sequence, in this case the end position penultimate; end of exchange occurs when no sort

time complexity:

  • Worst case: a column to be sorted in reverse order, the time complexity is O (n ^ 2)
  • Best case: ordered list to be sorted, the time complexity is 0 (n)

Space complexity: O (1)

def bubbleSort(arr):
    # 这里用lastIndex记录每一趟最后发生交换的位置,依次作为对普通冒泡排序的改进
    length = len(arr)
    change = length - 1
    while change:
        lastIndex = 0          # lastIndex记录该趟最后移动元素的位置
        for i in range(change):
            if a[i] > a[i+1]:
                a[i+1], a[i] = a[i], a[i+1]
                lastIndex = i + 1
        change = count      # 当该趟没有移动元素,lastIndex的值为0,结束排序

Selection Sort

The basic idea is simple selection sort:
\qquad Scanning the entire sequence from start to finish, and find the smallest key exchange key first, and then continue this and switching, eventually ordered sequence from the remaining keywords

  • Time complexity: O ( n 2 n^{2} )
  • Space complexity: O (1)
def selectSort(arr):
    length = len(arr)
    for i in range(length):
        minnumIndex = i
        for j in range(i+1, length):
            if arr[j] < arr[minnumIndex]:
                minnumIndex = j
        arr[i], arr[minnumIndex] = arr[minnumIndex], arr[i]

Heapsort

The stack can be seen as a complete binary tree, where large top stack, the complete binary tree root node is the maximum value.
The basic idea of the sort heap:
\qquad The initial sequence in order to write it in the form of binary tree from the bottom up for all non-leaf nodes, from right to left in turn to make adjustments (as required by its root of a binary tree is a large stack top), built stack is completed; At this point the root to the maximum, which is exchanged with the last node, the maximum value reached its final position, continue to do the same after adjustment for the rest of the binary tree nodes (this time only just put to the root need to be adjusted)

def adjust(arr, low, high):
    # 向下调整k位置上的结点
    i = low; j = 2*i;
    temp = arr[low]
    while i <= j and j < high:
        if arr[j] < arr[j+1]:         # 将左右结点中最大的结点当做arr[j]
            j += 1
        if arr[j] > temp:
            arr[i] = arr[j]
            i = j; j = 2*i            # 循环做对下一个根结点的调整
        else:
            break
    arr[i] = temp       # 存于最终位置
    
def heapSort(arr):
    length = len(arr)
    for i in range(length//2,-1,-1):    # 建堆
        adjust(arr, i ,length-1)
        
    # 将根结点与每一趟的最后一个结点交换,再调整
    for index in range(length-1, -1, -1):    
        arr[index], arr[0] = arr[0], arr[index]   # 该趟最大值已到最终位置
        adjust(arr, 0, index-1)                  # 新一轮的调整

Two: Binary Search

Achieve an ordered array of binary search algorithm

def Bsearch(arr, low, high, k):
    # 二分查找法
    while low <= high:
        mid = (low + high) // 2
        if arr[mid] == k:
            return mid
        elif arr[mid] < k:
            low = mid + 1
        else:
            high = mid - 1
    return high + 1

Fuzzy binary search algorithm (such as greater than or equal to the predetermined value of the first element)

def Bsearch(arr, low, high, k):
    # 模糊二分查找法查找大于等于给定值的第一个元素和其下标
    highTemp = high
    while low <= high:
        mid = (low + high) // 2
        if arr[mid] == k:
            while arr[mid-1] == k:
                mid -= 1
            return arr[mid],mid
        elif arr[mid] < k:
            low = mid + 1
        else:
            high = mid - 1
    if high+1 < highTemp:
        return arr[high+1],high+1
    else:
        return

Implemented in python programming Sqrt (x) (x square root)

def mySqrt(x):
    if x == 1:
        return 1
    left = 0
    right = x
    while left+1 < right:
        m = (right + left) / 2
        if m ** 2 < x:
            left = m
        elif m ** 2 == x:
            return int(m)
        else:
            right = m
        
    if int(right) ** 2 <= x:
        return int(right)
    else:
        return int(left)

Guess you like

Origin blog.csdn.net/shichensuyu/article/details/90301314