先占坑,再补充。
常用算法:
(1)排序:快排、归并排序、插入排序、希尔排序、桶排序;
(2)分治算法(divide-and-conquer),回溯算法,贪婪算法,动态规划(DP);
(3)二分查找(binary search);
一、排序算法
算法目标:
待排序数组S ---> 排序后 ---> 从小到大递增数组S'
1、快排(quick sort)
算法思路:
就是找出一个元素(枢纽元),然后将S划分成两个不相交的集合,其中一个集合S_small的所有元素都比枢纽元小,另外一个集合S_big的所有元素都比枢纽元大,然后对这两个集合递归进行以上操作;快速排序也是一种递归的分治算法。
算法复杂度:O(NlogN)
算法步骤:
(1)使用三数中值分割法来选出标兵P(也即在待排序数组S的首尾和中间位置三个元素选出最大的作为标兵P);
(2)将标兵与数组S最后一个元素交换位置;
(3)指针i指向数组S的首元素,指针j指向数组S的倒数第二个元素,指针i从左往右跳过比标兵P小的元素,停在大于等于P的元素位置上,而指针j从右往左跳过比标兵P大的元素,停在小于等于P的元素位置上,然后指针i和指针j交换指向元素的值;
(4)重复步骤(3),直到指针i在指针j的右边,也即i > j;
(5)把指针i指向的元素和S的最后一个元素交换位置,此时指针i左边的元素集合为S_small,都比指针i指向的元素小,但是无序,而指针i右边的元素集合为S_big,都比指针i指向的元素大,但是无序;
(6)对S_small和S_big递归执行(1)-(5)。
代码实现:
2、归并排序(merge sort)
算法思路:
把问题转化为将两个有序的序列合并成一个有序的序列,也即将一个无序数组等分为两个无序数组,然后对这两个无序数组应用归并排序算法变为有序数组,再合并,得到结果,这其实就是典型的分治策略。
算法复杂度:O(NlogN)
算法步骤:
如果S的元素个数小于2,则直接返回S,否则对S的前半部分和后半部分递归调用该归并算法,然后将返回结果,即两个有序的数组合并,即为最后的排序结果。
代码实现:
三、二分查找(binary search)
算法目标:
对于已经排序的数组S,查找元素target是否在S中,如果在,则返回位置,否则返回-1;
算法思路:
(1)将target与S[middle]元素比较,如果target > S[middle],则说明target元素有可能在S的middle+1~right区间中,否则就说明target元素有可能在S的left~middle-1区间中;
(2)对(1)中得到的新区间位置,重复(1),直到left > right;
代码实现: