数据结构之树

一、基本概念

二、考点

  1. 栈、队列、链表、字符串
  2. BFS和DFS
  3. 递归调用

二、

  1. 满二叉树
  2. 完全二叉树
  3. 线索二叉树
  4. 平衡二叉树
  5. 红黑树
  6. 哈夫曼树

三、算法

遍历算法

  1. 先序遍历:先遍历头结点,再遍历左子树,后遍历右子树
  2. 中序遍历:先遍历左子树,再遍历头结点,后遍历右子树
  3. 后序遍历:先遍历左子树,再遍历右子树,后遍历头结点
  4. 层序遍历

哈夫曼树

哈夫曼树的构造方法:

  1. 对给定的n个权值{W1,W2,W3,…,Wi,…,Wn}构成n棵二叉树的初始集合F={T1,T2,T3,…,Ti,…, Tn},其中每棵二叉树Ti中只有一个权值为Wi的根结点,它的左右子树均为空。
  2. 在F中选取两棵根结点权值最小的树作为新构造的二叉树的左右子树,新二叉树的根结点的权值为其左右子树的根结点的权值之和
  3. 从F中删除这两棵树,并把这棵新的二叉树同样以升序排列加入到集合F中。
  4. 重复2和3,直到集合F中只有一棵二叉树为止

数据结构:优先级队列

#include<iostream>
#include <queue>
#include <vector>
#include <functional>

struct HuffTree {
	int val;
	HuffTree* parent, *left, *right;
	HuffTree(int val, HuffTree* parent, HuffTree* left, HuffTree* right):val(val), parent(parent), left(left), right(right) {};
};
struct Descend {
	HuffTree* a;
	HuffTree* b;
	bool operator()(HuffTree* a, HuffTree* b) {
		return a->val > b->val;
	}
};
int* GenerateRandomArray(int size) {
	//生成随机大小的数组
	int* arr = new int[size];
	if (!arr) {
		std::cout << "bad alloc" << std::endl;
		return nullptr;
	}
	
	for (int i = 0; i < size; i++) {
		//生成随机大小的整数
		arr[i] =  1 + (int)rand() % (size + 1);
	}
	return arr;
}

void PreOrder(HuffTree* pRoot) {
	if (pRoot == nullptr) {
		return;
	}
	std::cout << pRoot->val << "\n";
	PreOrder(pRoot->left);
	PreOrder(pRoot->right);
}

void Clear(HuffTree* pRoot) {
	if (pRoot == nullptr) {
		return;
	}
	Clear(pRoot->left);
	Clear(pRoot->right);
	std::cout << pRoot->val << std::endl;
	delete[] pRoot;
	pRoot = nullptr;
	std::cout << "succeed delete node " << std::endl;
}


int main(int argc, char* argv[]) {
	std::priority_queue<HuffTree*, std::vector<HuffTree*>, Descend> Q;
	int size = 8;
	int* arr = GenerateRandomArray(size);
	//1、根据权值数组生成二叉树集合
	for (int i = 0; i < size; i++) {
		HuffTree* node = new HuffTree(arr[i], nullptr, nullptr, nullptr);
		std::cout << arr[i] << std::endl;
		if (!node) {
			std::cerr << "bad alloc" << std::endl;
			system("pasue");
			exit(1);
		}
		Q.push(node);
	}
	std::cout << "--------------------" << std::endl;
	//2、选择权值最小的两棵树作为新二叉树的左右子树
	HuffTree* root = nullptr;
	while (!Q.empty()) {
		if (Q.size() == 1) {
			break;
		}
		HuffTree* left = Q.top();
		std::cout << Q.top()->val << "\t";
		Q.pop();
		HuffTree* right = Q.top();
		std::cout << Q.top()->val << "\t" << left->val + right->val << "\n";
		Q.pop();
		root = new HuffTree(left->val + right->val, nullptr, left, right);
		if (!root) {
			std::cerr << "bad alloc" << std::endl;
			system("pasue");
			exit(1);
		}
		//3、将新树的头结点入队
		Q.push(root);
	}
	std::cout << "---------先序遍历-----------" << std::endl;
	HuffTree* temp = root;
	PreOrder(temp);
	std::cout << "---------后序删除-----------" << std::endl;
	Clear(root);
	system("pause");
	return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值