首页 > 代码库 > 108次练习之堆的声明及实现(二)

108次练习之堆的声明及实现(二)

  昨天写完堆的代码后,今天又敲了一下,顺便用到了函数对象,可以指定生成最小/大堆.

  (注释就懒得写了,有什么问题可以私下留言,或者看我上篇文章,毕竟本文仅供个人娱乐)

/*
*文件说明:堆的相关声明及实现(第二遍)
*作者:高小调
*日期:2016-12-27
*集成开发环境:Microsoft Visual Studio 2010 
*/
#include<vector>
template<typename T>
struct Min{
	bool operator()(T left,T right){
		return left<right;
	}
};
template<typename T>
struct Max{
	bool operator()(T left,T right){
		return left>right;
	}
};

template<typename T,typename class Type = Min<T>>
class Heap{
public:
	Heap(){}
	Heap(T arr[],size_t sz)
		:_a(arr,arr+sz){
		size_t LastNotLeapNode = (_a.size()-2)/2;
		for(int idx=LastNotLeapNode; idx>=0; --idx){
			_AdjustDown(idx);
		}
	}

	void Push(const T &e){
		_a.push_back(e);
		size_t LastNotLeapNode = (_a.size()-2)/2;
		_AdjustUp(LastNotLeapNode);
	}
	
	void Pop(){
		swap(_a[0],_a[_a.size()-1]);
		_a.pop_back();
		_AdjustDown(0);
	}
protected:

	void _AdjustDown(size_t idx){
		size_t parent = idx;
		size_t child = idx*2+1;
		while(child<_a.size()){

			if(child+1<_a.size() && Type()(_a[child+1],_a[child])){
				++child;	
			}

			if(Type()(_a[child],_a[parent])){
				swap(_a[child],_a[parent]);
				parent = child;
				child = parent*2+1;
			}else{
				break;
			}

		}
	}

	void _AdjustUp(size_t idx){
		size_t parent = idx;
		size_t child = 2*idx+1;
		while(child<_a.size() && child>parent){

			if(child+1<_a.size() && Type()(_a[child+1] , _a[child])){
				++child;
			}

			if(Type()(_a[child],_a[parent])){
				swap(_a[child],_a[parent]);
				child = parent;
				parent = (child-1)/2;
			}else{
				break;	
			}
		
		}
	}

private:
	vector<T> _a;
};

 

/*
*文件说明:测试文件
*作者:高小调
*日期:2016-12-26
*集成开发环境:Microsoft Visual Studio 2010 
*/
#include<iostream>
using namespace std;
#include"Heap2.h"
void TestHeap(){
	int arr[] = {10,16,18,12,11,13,15,17,14,19};
	size_t sz = sizeof(arr)/sizeof(arr[0]);
	Heap<int> h1(arr,sz);			//小堆
	Heap<int,Max<int>> h2(arr,sz);	//大堆
	h1.Pop();
	h1.Push(5);
	h2.Pop();
	h2.Push(20);
}
int main(){
	TestHeap();
	return 0;
}

   总结:

  第二遍再去敲堆的时候,就行云流水多了,但还是犯了个小错误:在构造函数中,没有给_a初始化...

  最基础的,就是最精华的!

  继续努力!

108次练习之堆的声明及实现(二)