左神算法基础class4—题目6判断一棵二叉树是否是平衡二叉树
1.题目:判断一棵二叉树是否是平衡二叉树
2.分析
(1)平衡二叉树的概念
平衡二叉树指对于任意节点,其左右节点高度差不超过1。满二叉树一定是平衡二叉树,平衡二叉树不一定是满二叉树。
对于4,5节点左右都为空,高度为0,差为0符合;
对于2节点,左高为0,右高为1,差为1符合;
对于3节点,左高为1,右高为0,差为1符合;
对于1节点,左高为2,右高为2,差为0符合;
所以上述树为平衡二叉树。
增加节点6后,对于3节点,左高为2,右高为0,不符合。
(2)二叉树题解套路
(可阅读树形dp问题)
-使用递归函数来求解二叉树某些问题,对于本题,所有节点都是平衡的,那么整颗树平衡。
- 1
对于当前节点x需要的信息如下(列出可能性):
①左平衡否:左不平衡则整颗树不平衡
②右平衡否:右不平衡则整颗树不平衡
在都平衡前提下再判断高度差,需要左右子树的高度信息:
③左高
④右高 - 2
设计递归返回结构:递归中需要平衡信息和高度信息 - 3
写代码
3.核心代码
(1)树的建立
//树结构
class Tree
{
public:
int val;
Tree* left;
Tree* right;
Tree(int num)
{
this->val = num;
right = NULL;
left = NULL;
}
};
//main函数中
Tree *head = new Tree(1);
head->left = new Tree(2);
head->left->right = new Tree(4);
head->right = new Tree(3);
head->right->left = new Tree(5);
head->right->left->right= new Tree(6);
(2)设计递归返回结构
需要高度信息和是否平衡的信息(true,false)
//返回信息类
class returnData
{
public:
int h; //高度
bool isB; //平衡否
returnData(bool isB,int h)//构造函数
{
this->h = h;
this->isB = isB;
}
};
(3)递归过程
思路:把整个过程视为一个黑盒,假设可以得到左树信息,再得到右树信息,对两棵子树求高度差并判断,最后向上返回。
对整个过程补充一些细节,①一开始时如果当前节点为空,返回平衡true、高度为0;②得到左树信息后如果子树平衡信息为false则直接返回false,右树也是同理;③最后如果高度差不大于1时,说明当前节点平衡,返回给其父节点的信息是平衡true,高度为当前节点高度最大值再加上当前节点(+1)
returnData* process(Tree* head)
{
if(head == NULL)//空树平衡,高度为0
return new returnData(true,0);
returnData* leftData = process(head->left);//假设可以在左树收到信息
if(!leftData->isB)//已经不平衡直接返回
return new returnData(false,0);
returnData* rightData = process(head->right);//假设可以在右树收到信息
if(!rightData->isB)//已经不平衡直接返回
return new returnData(false,0);
//在都平衡时求高度差
if(abs(leftData->h - rightData->h) > 1)
return new returnData(false,0);
//返回左右树最高高度加1
return new returnData(true,max(leftData->h , rightData->h) + 1);
}
(4)判断函数
我们只需要递归过程中平衡的信息
bool isBalance(Tree* head)
{
return process(head)->isB;
}
4.完整代码
#include<iostream>
using namespace std;
//树结构
class Tree
{
public:
int val;
Tree* left;
Tree* right;
Tree(int num)
{
this->val = num;
right = NULL;
left = NULL;
}
};
//需要返回的信息
class returnData
{
public:
int h; //高度
bool isB; //平衡否
returnData(bool isB,int h)//构造函数
{
this->h = h;
this->isB = isB;
}
};
//递归
returnData* process(Tree* head)
{
if(head == NULL)//空树平衡,高度为0
return new returnData(true,0);
returnData* leftData = process(head->left);//假设可以在左树收到信息
if(!leftData->isB)//已经不平衡直接返回
return new returnData(false,0);
returnData* rightData = process(head->right);//假设可以在右树收到信息
if(!rightData->isB)//已经不平衡直接返回
return new returnData(false,0);
//在都平衡时求高度差
if(abs(leftData->h - rightData->h) > 1)
return new returnData(false,0);
//返回左右树最高高度加1
return new returnData(true,max(leftData->h , rightData->h) + 1);
}
//判断函数
bool isBalance(Tree* head)
{
return process(head)->isB;
}
int main()
{
Tree *head = new Tree(1);
head->left = new Tree(2);
head->left->right = new Tree(4);
head->right = new Tree(3);
head->right->left = new Tree(5);
head->right->left->right= new Tree(6);
cout<<isBalance(head);
system("pause");
return 0;
}