数据结构之排序

1、直接插入排序

以下代码均为c语言

时间复杂度

最好情况o(n)

最差情况o(n^2)

	void InsertSort(int* a, int n)
	{
		for (int i = 0; i < n - 1; i++) {
			int end = i;
			int tmp = a[end + 1];
			while (end >= 0)
			{
				if (a[end] > tmp) {
					a[end + 1] = a[end];
					end--;
				}
				else {
					break;
				}
			}
			a[end + 1] = tmp;
		}
	}

2、希尔排序

时间复杂度o(n^1.3)

void ShellSort(int* a, int n) {
		int gap = n;
		while (gap > 1)
		{
			//推荐写法;除3
			gap = gap / 3 + 1;
			//gap=gap/2
			for (int i = 0; i < n - gap; i++)
			{
				int end = i;
				int tmp = a[end + gap];
				while (end >= 0)
				{
					if (a[end] > tmp) {
						a[end + tmp] = a[end];
						end -= gap;
					}
					else {
						break;
					}
				}
				a[end + gap] = tmp;
			}
		}

3、直接选择排序

时间复杂度o(n^2)

3.1选择排序 
//选择排序
void SelectSort(int* a,int n){
	int begin = 0, end = n - 1;
	while (begin < end)
	{
		int mini = begin, maxi = begin;
		for (int i = begin; i <= end; i++)
		{
			if (a[i] > a[maxi]) {
				maxi - i;
			}
			if (a[i] < a[mini]) {
				mini = i;
			}
		}
		if (begin = maxi) {
			maxi = mini;
		}
		Swap(&a[mini], &a[begin]);
		Swap(&a[maxi], &a[end]);
		++begin;
		--end;
	}
3.2堆排序

时间复杂度o(nlogn)

//向下调整
	void adjustDown(int* a, int n, int parent) {
		int child = parent * 2 + 1;
		while (child < n)
		{
			//左右子节点进行比较,找到子节点中较大的那个
			if (chid + 1 < n && a[child] < a[child + 1]) {
				child++;
			}
			//和父节点进行比较大于就交换
			if (a[child] > a[parent]) {
				Swap(&a[child], &a[parent]);
				parent = child;
				child = parent * 2 + 1;
			}
			else {
				break;
			}
		}
	}
	//2、堆排序
	void HeapSort(int* a, int n) {
		//1、建堆
		//parent=(child-1)/2
		for (int i = (n - 1 - 1) / 2; i >= 0 / i--)
		{

			adjustown(a, n, i);
		}
		//2、堆排序
		int end = n - 1;
		while (end > 0)
		{
			Swap(&a[0], &a[end]);
			end--;
			adjustDown(a, end, 0);
		}
	}

4、交换排序

冒泡排序就像烧水一样先将较大的数冒出来

 4.1冒泡排序
//1、冒泡排序、
	void BubbleSort(int* a, int n) {
		int exchange = 0;
		for (int i = 0; i < n; i++)
		{
			for (int j = 0; j < n - i - 1; j++)
			{
				if (a[j] > a[j + 1]) {
					exchange = 1;
					Swap(&a[j], &a[j + 1]);
				}
			}
			if (exchange == 0) {
				break;
			}
		}
	}
4.2快速排序
 
//第一种解法:hoare版本
int _QuickSort(int* a, int left, int right) {
    int key = left;
    while (left < right) {
        // 从右往左遍历,找比基准值要小的
        while (left < right && a[right] >= a[key])
            --right;
        // 从左往右遍历,找比基准值要大的
        while (left < right && a[left] <= a[key])
            ++left;
        Swap(&a[left], &a[right]);
    }
    Swap(&a[left], &a[key]);
    return left;
}

// 2. 快速排序
void QuickSort(int* a, int left, int right) {
    if (left >= right) {
        return;
    }
    int meet = _QuickSort(a, left, right);
    QuickSort(a, left, meet - 1);
    QuickSort(a, meet + 1, right);
}
//第二种解法:挖坑法
// 2. 挖坑法
int _QuickSort(int* a, int left, int right) {
    int hole = left;
    int key = a[hole];
    while (left < right) {
        while (left < right && a[right] >= key) {
            --right;
        }
        a[hole] = a[right];
        hole = right;
        
        while (left < right && a[left] <= key) {
            ++left;
        }
        a[hole] = a[left];
        hole = left;
    }
    a[hole] = key;
    return hole;
}

 5、归并排序

基本思想:归并排序是建立在归并操作上的一种有效的排序算法,该算法是采用分治法的一个非常典型的应用,将已有序的子序列合并,得到完全有序的序列;即先使每个子序列有序,再使子序列段间有序,若将两个有序表合并成一个有序表,称为二路归并。

void _MergeSort(int* a, int left, int right, int* tmp) {
    if (left >= right) {
        return;
    }

    int mid = (right + left) / 2;
    // [left, mid] [mid+1, right]
    _MergeSort(a, left, mid, tmp);
    _MergeSort(a, mid + 1, right, tmp);
    int begin1 = left, end1 = mid;
    int begin2 = mid + 1, end2 = right;
    int index = begin1;

    // 合并两个有序数组为一个数组
    while (begin1 <= end1 && begin2 <= end2) {
        if (a[begin1] < a[begin2]) {
            tmp[index++] = a[begin1++];
        } else {
            tmp[index++] = a[begin2++];
        }
    }

    while (begin1 <= end1) {
        tmp[index++] = a[begin1++];
    }

    while (begin2 <= end2) {
        tmp[index++] = a[begin2++];
    }

    for (int i = left; i <= right; i++) {
        a[i] = tmp[i];
    }
}

void MergeSort(int* a, int n) {
    int* tmp = (int*)malloc(sizeof(int) * n);
    _MergeSort(a, 0, n-1, tmp);
    free(tmp);
}

  • 9
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值