幾個內部排序演算法的總結(JAVA版)
阿新 • • 發佈:2018-12-26
插入排序
1、直接插入排序
public void insertSort(int[] a){
for(int i=0;i<a.length;i++){
int key=a[i];
int pos=i;
while(pos>0&&a[pos-1]>key){
a[pos]=a[pos-1];
pos--;
}
a[pos]=key;
}
for(int i=0;i<a.lenght;i++){
System.out.print(a[i]+" ");
}
}
直接插入排序(Straight Insertion Sort)是一種最簡單的排序方法:將一個記錄插入到已排好的有序表中,從而得到一個新的、記錄數增1 的有序表。
時間複雜度O(n2),空間複雜度O(1),穩定。
2、希爾排序
希爾排序(Shell‘s Sort)又稱為“最小增量排序”:先將整個帶排記錄分割成為若干子序列分別進行直接插入排序,待整個序列中的記錄“基本有序”時,再將全體記錄進行一次直接插入排序。詳細說明:先將要排序的一組數按增量d(d=n/2,n為待排個數)分成若干組,對每組中全部元素進行直接插入排序,然後按d/2增量分組,直至d=1結束。public void shellSort(int[] a){ double=d1.length; int temp=0; while(true){ d1=Math.ceil(d1/2); int l=(int)d1; for(int i=0;i<l;i++){ for(int j=i+l;j<a.length;j++){ int n=j-l; temp=a[j]; for(;n>=0&&temp<a[n];n-=1) a[n+l]=a[n]; a[n+1]=temp; } } if(l==1) break; }//while }
時間複雜度O(n2),不穩定。
快速排序
3、氣泡排序
氣泡排序(Bubble Sort)比較簡單就不講了。public void bubbleSort(int[] a){ int temp=0; for(int i=0;i<a.length;i++){ for(int j=i;j<a.length;j++){ if(a[i]>a[j]){ temp=a[i]; a[i]=a[j]; a[j]=temp; } } } }
時間複雜度O(n2),穩定。
4、快速排序
public void QuickSort(int[] a,int low,int high){
int dp;
if(low<high){
dp=partition(a,low,high);
QuickSort(a,low,dp-1);
QuickSort(a,dp+1,high);
}
}
public static int partiton(int[] a,int left,int right({
int pivot=a[left];
while(left<right){
while(left<right&&a[right]>=pivot){
right--;
}
if(left<right){
a[left++]=a[right];
}
while(left<right&&a[left<=pivot){
left++;
}
if(left<right){
a[right--]=a[left];
}
}
a[left]=pivot;
return left;
}
快速排序(Quick Sort)是對氣泡排序的一種改進:通過一趟排序將待排記錄分割成獨立的兩部分,其中一部分記錄的關鍵字均比另一部分記錄的關鍵字小,則可分別對這兩部分記錄繼續進行排序,以達到整個序列有序。一趟排序的詳細說明:設樞軸記錄的關鍵字為pivotkey,則首先從high所指位置起向前搜尋找到第一個關鍵字小於pivotkey的記錄和樞軸記錄交換,然後從low所指位置起向後搜尋,找到第一個關鍵字大於pivotkey的記錄和樞軸記錄交換,重複步驟直到low=high。
時間複雜度O(nlogn),空間複雜度O(logn),不穩定。平均效能最好!!!
選擇排序
5、簡單選擇排序
public SelectSort(int[] a){
int min=0,temp=0;
for(int i=0;i<a.length;i++){
min=i;
for(int j=i+1j<a.length;j++){
if(a[j]<a[min])
min=j;
}
if(min!=i){
a[i]<->a[min];
}
}
}
選擇排序(Simple Selection Sort)是選擇關鍵字最小的記錄作為有序序列的第i個記錄。
時間複雜度O(n2),不穩定。
6、堆排序
public void HeapSort(int[] a){
for(int i=0;i<a.length;i++){
createMaxHeap(a,a.length-1-i);
swap(a,0,a.length-1-i);
}
}
public static void createMaxHeap(int[] a,int last){
for(int i=(last-1)/2;i>=0;i--){
int k=i;//儲存當前節點
while(a*k+1<=last){//當前節點存在子節點
int big=2*k+1;
if(big<last){//如果右子節點存在
if(a[big]<<a[big+1])
big++;
}
if(a[k]<a[big]){
swap(a,k,big);
k=big;
}else{
break;
}
}
}
}
pubilc static void swap(int[] a,int i,int j){
if(i==j){
return;
}
a[i]<->a[j];
}
堆排序(Heap Sort)每一趟排序的基本操作將當前無序區的堆頂記錄R[1]和該區間的最後一個記錄交換,然後將新的無序區調整為堆。
時間複雜度O(nlogn),空間複雜度O(1)。
歸併排序
7、2路歸併排序
public void Sort(int[] a,int low,int high){
int mid=(low+high)/2;
if(low<high){
Sort(a,low,mid);//左邊
Sort(a,mid+1,high);//右邊
merge(a,low,mid,high);
}
}
public void merge(int[] a,int low,int mid,int high){
int[] temp=new int[high-low+1];
int i=low;
int j=high;
int k=0;
while(i<=mid&&j<=high){
if(a[i]<a[j]){
temp[k++]=a[i++];
}else{
temp[k++]=a[j++];
}
}//while
while(i<mid){
temp[k++]=a[i++];
}
<pre name="code" class="java"> while(j<high){
temp[k++]=a[j++];
}
for(int x=0;x<temp.length;x++){a[x+low]=temp[x];
}
}
2路-歸併排序(Merging Sort)是將兩個有序表合併成一個新的有序表。
時間複雜度O(nlogn),空間複雜度O(n),穩定。
計數排序
8、計數排序
public CountSort(int[] a){
int k=a.lenght;
int[] res=new int[k];
int count[]=new int[k];
for(int i=0;i<k;i++){//初始化
count[i]=0;
}
//將陣列中的重複的次數
for(int i=0;i<a.length;i++){
count[a[i]]=count[a[i]+1];
}
for(int i=1;i<k;i++){
count[i]=count[i]+count[i-1];
}
//將陣列a中的元素按順序複製到res中
for(int i=a.length-1;i>=0;i--){
res[count[a[i]]-1]=a[i];
count[a[i]]--;
}
}
計數排序不需要倆個數之間的對比呦~