題意:
給你一個樹的先序遍歷,讓你判斷是否爲red-black tree. 另外告訴你是一個二叉查找樹(BST)。
思路:
先說一下什麼是紅黑樹:
紅黑樹(Red Black Tree) 是一種自平衡二叉查找樹,是在計算機科學中用到的一種數據結構,紅黑樹和AVL樹類似,都是在進行插入和刪除操作時通過特定操作保持二叉查找樹的平衡,從而獲得較高的查找性能.
紅黑樹是一種平衡二叉樹,但並不是完美的平衡二叉樹,也就是並不滿足左右深度絕對值差1,所以這裏我們無需判斷是否平衡.
紅黑樹的性質:
1.節點可以是黑的或紅的
2.根節點一定是黑的
3.所有葉節點是黑的.(注意這裏的葉節點是NIL結點)
4.如果一個結點時紅的,那麼他的子結點一定是黑的.
5.從任意結點到每個葉節點的簡單路徑上經過黑色結點的個數相同.
所以這個題目我們根據先序遍歷,利用BST樹的性質建樹即可.然後爆搜判斷一下就好了.性質5可以轉化爲直接從根節點開始到每個葉節點的黑色結點個數相同.
#include<bits/stdc++.h>
using namespace std;
const int maxn = 50;
struct node
{
int val,col;
node *l;
node *r;
node()
{
l = r = nullptr;
}
};
int n,flag;
node *Insert(node *root,int val)
{
if(root == nullptr)
{
node *tmp = new node;
tmp -> val = abs(val);
tmp -> col = val > 0 ? 1:0;
return tmp;
}
if(abs(val) < root -> val)
root -> l = Insert(root -> l,val);
else
root -> r = Insert(root -> r,val);
return root;
}
//vector<int>vt;
int num,leaf ;
void dfs(node *root,int s)
{
if(flag == 0) return ;
if(root == nullptr)
{
if(num == -1) num = s;
else if(num != s) flag = 0;
return ;
}
if(root -> col == 1) s++;
else
{
if(root -> l && root -> l -> col == 0) flag = 0;
if(root -> r && root -> r -> col == 0) flag = 0;
}
dfs(root -> l,s);
dfs(root -> r,s);
return ;
}
int main()
{
int _;
cin >>_;
while(_--)
{
//vt.clear();
flag = 1;
leaf = 0;
num = -1;
scanf("%d",&n);
node *root = nullptr;
for(int i = 1;i <= n;++i)
{
int x;
scanf("%d",&x);;
root = Insert(root,x);
}
if(root -> col == 0)
{
puts("No");
continue;
}
dfs(root,0);
if(flag)
puts("Yes");
else
puts("No");
}
return 0;
}