1. 程式人生 > >題解 對稱二叉樹

題解 對稱二叉樹

div get return href spa fin tree 二叉樹 https

題面:

https://www.luogu.org/problemnew/show/P5018

解析

這題看上去好像很復雜(實際上也很復雜)。。。

但仔細想想,

若以一個點v為根的子樹為對稱二叉樹,

則它的左子樹lson和右子樹rson一定是對稱的,即:

lson的左子樹和rson的右子樹是對稱的且lson的右子樹和rson的左子樹是對稱的。

看出規律了吧,

這樣只要遞歸求解就行了!!

終止條件就應該是:lson=rson=-1;

然後,先遍歷一遍,求出以每個點為根的節點數目,再枚舉就能AC了!!

上AC代碼:

 1 #include <bits/stdc++.h>
 2
using namespace std; 3 4 struct tree{ 5 int ls,rs; 6 int w,sonsum; 7 int id; 8 }; 9 tree a[1000001]; 10 int n; 11 int ls=0,rs=1,ans=0; 12 13 bool dfs(int x,int y){ 14 if(x==-1&&y==-1) return 1; 15 else if(x==-1||y==-1) return 0; 16 int xl=a[x].ls,xr=a[x].rs;
17 int yl=a[y].ls,yr=a[y].rs; 18 if(dfs(xl,yr)&&dfs(xr,yl)){ 19 if(a[x].w==a[y].w) return 1; 20 } 21 return 0; 22 } 23 24 int find(int x){ 25 if(x==-1) return 0; 26 a[x].sonsum=find(a[x].ls)+find(a[x].rs); 27 return ++a[x].sonsum; 28 } 29 30 int
main(){ 31 scanf("%d",&n); 32 for(int i=1;i<=n;i++){ 33 scanf("%d",&a[i].w); 34 a[i].id=i; 35 } 36 for(int i=1;i<=n;i++){ 37 scanf("%d%d",&a[i].ls,&a[i].rs); 38 } 39 find(1); 40 for(int i=1;i<=n;i++){ 41 if(dfs(a[i].ls,a[i].rs)){ 42 ans=max(ans,a[i].sonsum); 43 } 44 } 45 printf("%d\n",ans); 46 return 0; 47 }

題解 對稱二叉樹