归并排序和选择排序:Java 和c实现

1.归并排序与选择排序

归并排序定义:归并排序就是将两个或两个以上的有序表合并成一个有序表的过程。将两个有序表合并成一个有序表的过程称为2-路归并。

选择排序定义:每一趟从待排序的记录中选出关键字最小的记录,按顺序放在已排序的记录序列的最后,直到全部排完为止。

注意:1.选择是把一个文件分成包含k个最小元素和n-k个最大元素的两个部分的过程。

2.选择和归并互为逆操作:选择是把一个序列分成两部分,归并把两个文件合并成一个文件

3.归并排序是快速排序的补充

4.归并排序以连续的方式访问数据

5.归并排序适用于链表排序。

6.归并排序对输入的初始次序不敏感。

2.归并排序全过程

4 9 15 24 30

(画图功力不行,还是贴图吧,,,,)

 

 

 

 

此时,比较结束后,把A中左项或子项剩余的元素整体复制到B中去,排序完成。

排序算法如下:


void Merge(SqList L,int low,int m,int high)
{
	
	int B[high-low+1];
	int i=low,j=m+1,k=0;
	while(i<=mid&&j<=high)
	{
		B[k++]=L.elem[i]<=L.elem[j]?L.elem[i++]:L.elem[j++];
	}
	while(i<=mid) B[k++]=L.elem[i++];
	while(j<=high) B[k++]=L.elem[j++];
	for(i=low,k=0;i<=high;i++)
	{
		L.elem[i]=B[k++];
	}
	delete []B;
	} 

当然这个算法的前提是两个排好序的表合并成一个表,那么如何解决一个乱序表的排序问题呢,其实可以利用递归思想,即把一个乱序表分成两个子序表,再把子序表各自分出两个子子序表,,,直到分到序列表长度为1为止,此时两两进行排序,不断的向回排序。

递归算法:

void MergeSort(SqList L,int low,int high)  
{     
    /*用分治法进行二路归并排序*/  
    int mid;  
    if(low<high)  /*区间长度大于1*/
    {      
        mid=(low+high)/2;               /*分解*/
        MergeSort(L,low,mid);           /*递归地对low到mid序列排序 */ 
        MergeSort(L,mid+1,high);        /*递归地对mid+1到high序列排序 */ 
        Merge(L,low,mid,high);          /*归并*/  
    }  
}

3.

归并排序分析:

归并排序将输入序列分成两部分并递归地处理每一部分。当子问题解决后,算法又将子问题地解合并。假设具有n个元素地归并排序地复杂度表示为T(n),则归并排序的递归式可定义为:

T(n)=2T(n/2)+O(n);

根据分治法主定理:T(n)=O(nlogn)

4.性能

最坏情况下时间复杂度:O(nlogn)

最好情况下时间复杂度:O(nlogn)

平均情况下时间复杂度:O(nlogn)

最坏情况下空间复杂度:O(n)辅助

选择排序:

选择排序是一种原地排序算法,适用于小文件,由于选择操作是基于键值的且交换操作只在需要时才执行,所以选择排序常用于数值较大和键值较小的文件。

优点:容易实现,原地排序不需要额外的存储空间

缺点:扩展性较差:O(n^2)

算法:

1.寻找序列中的最小值。

2.用当前位置的值交换最小值。

3.对于所有元素重复上述过程,直到整个序列排序完成。

void Selection(int A[],int n)
    int i,j,min,temp;
for(i=0;i<n-1;i++)
    {
        min=i;
        for(j=i+1;j<n;j++)    
            {
                if(A[j]<A[min])
                    {
                        min=j;
                    }
           temp=A[min];
            A[min]=A[i];
            A[i]=temp;
            }
       }

最坏情况时间复杂度:O(n^2)

最好情况时间复杂度:O(n)

最坏情况下空间复杂度:O(1)

 

 

 

 

 

附归并排序Java代码

package cn.sal.paixu;

import java.util.Arrays;

public class MergeSort {

	public static void mergeSort(int[] arr) {
		if (arr == null || arr.length < 2) {
			return;
		}
		mergeSort(arr, 0, arr.length - 1);
	}

	public static void mergeSort(int[] arr, int l, int r) {
		if (l == r) {
			return;
		}
		int mid = l + ((r - l) >> 1);
		mergeSort(arr, l, mid);
		mergeSort(arr, mid + 1, r);
		merge(arr, l, mid, r);
	}

	public static void merge(int[] arr, int l, int m, int r) {
		int[] help = new int[r - l + 1];
		int i = 0;
		int p1 = l;
		int p2 = m + 1;
		while (p1 <= m && p2 <= r) {
			help[i++] = arr[p1] < arr[p2] ? arr[p1++] : arr[p2++];
		}
		while (p1 <= m) {
			help[i++] = arr[p1++];
		}
		while (p2 <= r) {
			help[i++] = arr[p2++];
		}
		for (i = 0; i < help.length; i++) {
			arr[l + i] = help[i];
		}
	}

	// for test
	public static void comparator(int[] arr) {
		Arrays.sort(arr);
	}

	// for test
	public static int[] generateRandomArray(int maxSize, int maxValue) {
		int[] arr = new int[(int) ((maxSize + 1) * Math.random())];
		for (int i = 0; i < arr.length; i++) {
			arr[i] = (int) ((maxValue + 1) * Math.random()) - (int) (maxValue * Math.random());
		}
		return arr;
	}

	// for test
	public static int[] copyArray(int[] arr) {
		if (arr == null) {
			return null;
		}
		int[] res = new int[arr.length];
		for (int i = 0; i < arr.length; i++) {
			res[i] = arr[i];
		}
		return res;
	}

	// for test
	public static boolean isEqual(int[] arr1, int[] arr2) {
		if ((arr1 == null && arr2 != null) || (arr1 != null && arr2 == null)) {
			return false;
		}
		if (arr1 == null && arr2 == null) {
			return true;
		}
		if (arr1.length != arr2.length) {
			return false;
		}
		for (int i = 0; i < arr1.length; i++) {
			if (arr1[i] != arr2[i]) {
				return false;
			}
		}
		return true;
	}

	// for test
	public static void printArray(int[] arr) {
		if (arr == null) {
			return;
		}
		for (int i = 0; i < arr.length; i++) {
			System.out.print(arr[i] + " ");
		}
		System.out.println();
	}

	// for test
	public static void main(String[] args) {
		int testTime = 500000;
		int maxSize = 100;
		int maxValue = 100;
		boolean succeed = true;
		for (int i = 0; i < testTime; i++) {
			int[] arr1 = generateRandomArray(maxSize, maxValue);
			int[] arr2 = copyArray(arr1);
			mergeSort(arr1);
			comparator(arr2);
			if (!isEqual(arr1, arr2)) {
				succeed = false;
				printArray(arr1);
				printArray(arr2);
				break;
			}
		}
		System.out.println(succeed ? "Nice!" : "Fucking fucked!");

		int[] arr = generateRandomArray(maxSize, maxValue);
		printArray(arr);
		mergeSort(arr);
		printArray(arr);

	}

}

 

 

 

 

posted @ 2019-04-05 10:45  ch_musk  阅读(497)  评论(0编辑  收藏  举报