算法自学笔记:二叉堆实现优先队列

二叉堆是一种特殊的二叉树,满足两个条件:
1 二叉堆完全平衡,就是说除了最底层,上面都完全填满
2 二叉堆节点有序,对于每一个父节点都大于等于子节点。

尽管书上一般用图表示二叉堆,但是在计算机里实现二叉堆并不需要真正构造节点和边,而是构造一个数组,每个元素代表节点,而索引之间代数关系代表链接。

二叉堆的性质:
1 a[1](根节点)为最大值
// 注意一般取a[1]而非a[0]为根,以简便运算
2 使用数组索引在堆上移动:
对于k索引节点: 父节点 k / 2
子节点2k 2k + 1

二叉堆操作:
1 上浮
如果二叉堆中一个子节点大于了父节点,重复将该子节点和其父节点交换,直到满足子节点小于父节点或者达到根

private void swim(int k) {
   
		while (k > 1 && less(pq[k / 2], pq[k])) {
   
			exch(pq, k / 2, k);	// switch the node with father
			k /= 2;	// new position of k
		}
}

利用swim方法我们可以实现在堆里插入新元素。首先把该元素放到堆末尾,然后使用swim将其归位

private void insert(Key v) {
   
	N++;
	pq[N] = v;
	swim(N);
}

2下沉
如果二叉堆一个父节点小于了子节点,重复将该节点和其最大的子节点交换,直到满足父节点大于子节点或达到堆底

private void sink(int k) {
   
		while (k * 2 <= N) {
   
			int j = 2 * k;
			if (j < N && 
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值