冒泡排序:
思想:(1)对数组中的的个数据,依次比较相邻的两个元素的大小
(2)如果前面的数据大于后面的数据,那么交换这两个数据
(3)用同样的方法,将剩下的数据逐一比较
平均的时间复杂度是:O(n^2) 最坏:O(n^2)
选择排序:
思想:
(1)将原始数组中选择一个最小的数据,将其和第一个位置的数据交换
(2)接着从剩下的n-1个数据中选择次小的数据,将其和第二个位置交换
(3)然后不断重复上述过程,知道最后两个数据不再交换
思想:
(缩小增量排序)
(1)将n个元素的数组分成n/2个数字序列,第一个数据和第n/2+1为一对......
(2)一次循环使得每个序列对排好序
(3)然后变成n/4个序列,再次排序
(4)不断重复上述过程,随着序列减少变为最后一个,也就完成了排序
平均时间复杂度:O(n^3/2) 最坏:O(n^2)
快速排序:
思想:
(1)首先设定一个分界值,以分界值将数据分为左右两部分
(2)将大于分界值的放在数组的右侧,小于分界值的放在数组的左侧
(3)然后,左边和右边的数据独立排序,对于左侧的的数据又可以取一个分界值,将其有分成左右两个部分,同样左边放置较小值,右边放置较大值,右侧的数组也是进行同样的操作。
(4)重复以上操作,可以看出这是一个递归定义,通过将左侧部分排好序后,再递归排好右侧部分顺序,左右两部分的数据排好序后,整个数组也就完成了整个数组的排序
平均时间复杂度:O(nlogn) 最坏:O(n^2)
归并排序:
思想:
将含有n个待排序的数据序列看成n个长度为1的有序子表组成,将其依次两两合并然后再对其两两合.....重复这个过程,直到最后长度为n;
平均时间复杂度:O(nlogn)最坏:O(nlogn)
桶排序O(n)、基数排序O(dn) ----d实常数
不稳定的排序:
快速排序、希尔排序、堆排序O(nlogn)、选择排序
思想:(1)对数组中的的个数据,依次比较相邻的两个元素的大小
(2)如果前面的数据大于后面的数据,那么交换这两个数据
(3)用同样的方法,将剩下的数据逐一比较
平均的时间复杂度是:O(n^2) 最坏:O(n^2)
public void bubbleSort(int []array){
for(int i = 1;i<array.length;i++){
for(int j =0;j<array.length-i;j++){
if(array[j]>array[j+1]){
int temp = array[j];
array[j] = array[j+1];
array[j+1] = temp;
}
}
}
}
选择排序:
思想:
(1)将原始数组中选择一个最小的数据,将其和第一个位置的数据交换
(2)接着从剩下的n-1个数据中选择次小的数据,将其和第二个位置交换
(3)然后不断重复上述过程,知道最后两个数据不再交换
平均时间复杂度:O(n^2)最坏:O(n^2)
public void selectSort(int []array){
for(int i = 0;i<array.length-1;i++){
int index =i;
for(int j =i+1;j<array.length;j++){
if(array[j]<array[index]){
index = j;
}
}
if(index!=i){
int temp = array[i];
array[i] = array[index];
array[index] = temp;
}
}
}
插入排序:
思想:
(1)首先对数组的前两个数据进行从小到大的排序
(2)接着第3个数据和前两个数据进行比较,将第3个位置插入到合适的位置
(3)然后第4个进行第三步
(4)不断重复,知道最后一个数据插入到合适的位置
平均时间复杂度:O(n^2)最坏:O(n^2)
public void insertSort(int []array){
for(int i=1;i<array.length;i++){
int t = array[i];
int j = i-1;
while(j>=0&&t<array[j]){
array[j+1] =array[j];
j--;
}
array[j+1] = t;
}
}
希尔排序:
思想:
(缩小增量排序)
(1)将n个元素的数组分成n/2个数字序列,第一个数据和第n/2+1为一对......
(2)一次循环使得每个序列对排好序
(3)然后变成n/4个序列,再次排序
(4)不断重复上述过程,随着序列减少变为最后一个,也就完成了排序
平均时间复杂度:O(n^3/2) 最坏:O(n^2)
public void shellSort(int []array){
for(int r = array.length;r>=1;r/=2){
for(int i = r;i<array.length;i++){
int temp = array[i];
int j = i-r;
while(j>=0&&temp<array[j]){
array[j+r] = array[j];
j-=r;
}
array[j+r] =temp;
}
}
}
快速排序:
思想:
(1)首先设定一个分界值,以分界值将数据分为左右两部分
(2)将大于分界值的放在数组的右侧,小于分界值的放在数组的左侧
(3)然后,左边和右边的数据独立排序,对于左侧的的数据又可以取一个分界值,将其有分成左右两个部分,同样左边放置较小值,右边放置较大值,右侧的数组也是进行同样的操作。
(4)重复以上操作,可以看出这是一个递归定义,通过将左侧部分排好序后,再递归排好右侧部分顺序,左右两部分的数据排好序后,整个数组也就完成了整个数组的排序
平均时间复杂度:O(nlogn) 最坏:O(n^2)
public static void quickSort(int[] keys) {
quickSort(keys, 0, keys.length-1);
}
private static void quickSort(int[] keys, int begin, int end)
{
if (begin>=0 && begin<keys.length && end>=0 && end<keys.length && begin<end)
{
int i=begin, j=end;
int vot=keys[i];
while (i!=j)
{
while (i<j && keys[j]>=vot)
j--;
if (i<j)
keys[i++]=keys[j];
while (i<j && keys[i]<=vot)
i++;
if (i<j)
keys[j--]=keys[i];
}
keys[i]=vot;
quickSort(keys, begin, j-1);
quickSort(keys, i+1, end);
}
}
归并排序:
思想:
将含有n个待排序的数据序列看成n个长度为1的有序子表组成,将其依次两两合并然后再对其两两合.....重复这个过程,直到最后长度为n;
平均时间复杂度:O(nlogn)最坏:O(nlogn)
public void merge(int a[],int s,int m,int t,int []temp){
//temp =new int[t-s+1];
int i = s,j =m+1,k =0;
while(i<m&&j<=t){
if(a[i]<a[j]){
temp[k] = a[i];
k++;
i++;
}else{
temp[k] = a[j];
j++;
k++;
}
}
while(i<m){
temp[k] = a[i];
k++;
i++;
}
while(j<=t){
temp[k] = a[i];
j++;
k++;
}
while(s<=t){
a[s++] = temp[k++];
}
}
public void mergeSort(int array[],int l,int r,int []temp){
if(l<r){
int mid = (l+r)/2;
mergeSort(array,l,mid,temp);
mergeSort(array,mid+1,r,temp);
merge(array,l,mid,r,temp);
}
}
public void mergeSort(int []arr){
int []temp = new int[arr.length];
mergeSort(arr, 0, arr.length-1, temp);
}
桶排序O(n)、基数排序O(dn) ----d实常数
不稳定的排序:
快速排序、希尔排序、堆排序O(nlogn)、选择排序