数据结构——堆排序

堆排序

1.堆

1.概念:本质上就是存储一棵完全二叉树的数组。

2.性质:

大堆:根节点>左孩子&&根节点>右孩子;

小堆:根节点<左孩子&&根节点<右孩子。

2.堆排序的实现

1.思路:

(1)对待排数组进行建堆操作

(2)每次取出首元素--最值放入另一个临时数组中来存放

(3)将临时数组中的值拷贝到原数组中去

过程:

2.实现:

降序--大堆

升序--小堆

#include <stdio.h>
#include <stdlib.h>

typedef struct Heap {
	int* arr;
	int size;
	int capacity;
}Heap;

//1.堆的向下调整:只有pos下标处的元素有问题,其他位置均没有问题
//以建大堆为例	: 根节点 > 左孩子  &&  根节点 > 右孩子
void adjustDown(Heap* ph, int pos) {
	int left = pos * 2 + 1;
	int right = pos * 2 + 2;
	while (1) {
		//判断是否是叶子结点了
		if (pos >= ph->size -1 || left > ph->size - 1) {
			break;
		}
		int max = left;		//记录左右孩子中较大的下标
		//判断有无右孩子
		if (right <= ph->size - 1 && ph->arr[right] > ph->arr[left]) {
			max = right;
		}
		if (ph->arr[pos] > ph->arr[max]) {
			break;
		}
		//开始交换
		int temp = ph->arr[max];
		ph->arr[max] = ph->arr[pos];
		ph->arr[pos] = temp;

		pos = max;
		left = pos * 2 + 1;
		right = pos * 2 + 2;
	}
}

void heapCreate(Heap* ph) {
	for (int i = (ph->size - 2) / 2; i >= 0; --i) {
		adjustDown(ph, i);
	}
}

void heapSort(Heap* ph) {
	heapCreate(ph);
	int* newarr = (int*)malloc(sizeof(int)*ph->capacity);
	for (int i = 0; i < ph->capacity; ++i) {
		newarr[i] = ph->arr[0];
		ph->arr[0] = ph->arr[ph->size];
		--ph->size;
		adjustDown(ph, 0);
	}
	ph->size = ph->capacity;
	free(ph->arr);
	ph->arr = NULL;
	ph->arr = newarr;
}



int main() {
	Heap ph;
	int capacity = 10;
	ph.arr = (int*)malloc(sizeof(int)*capacity);
	ph.capacity = ph.size = capacity;
	for (int i = 0; i < ph.size; ++i) {
		ph.arr[i] = i;
	}
	printf("\n");
	for (int i = 0; i < ph.size; ++i) {
		printf("%d  ", ph.arr[i]);
	}
	printf("\n");
	heapCreate(&ph);

	for (int i = 0; i < ph.size; ++i) {
		printf("%d  ", ph.arr[i]);
	}

	heapSort(&ph);
	printf("\n排序后:");
	for (int i = 0; i < ph.size; ++i) {
		printf("%d  ", ph.arr[i]);
	}


	system("pause");
	return 0;
}

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值