1. 程式人生 > >codevs——T1814 最長鏈

codevs——T1814 最長鏈

可能 ble 二叉 content amp color nbsp -s style

http://codevs.cn/problem/1814/

時間限制: 1 s 空間限制: 256000 KB 題目等級 : 鉆石 Diamond

題目描述 Description

現給出一棵N個結點二叉樹,問這棵二叉樹中最長鏈的長度為多少,保證了1號結點為二叉樹的根。

輸入描述 Input Description

輸入的第1行為包含了一個正整數N,為這棵二叉樹的結點數,結點標號由1至N。

接下來N行,這N行中的第i行包含兩個正整數l[i], r[i],表示了結點i的左兒子與右兒子編號。如果l[i]為0,表示結點i沒有左兒子,同樣地,如果r[i]為0則表示沒有右兒子。

輸出描述 Output Description

輸出包括1個正整數,為這棵二叉樹的最長鏈長度。

樣例輸入 Sample Input

5

2 3

4 5

0 6

0 0

0 0

樣例輸出 Sample Output

4

數據範圍及提示 Data Size & Hint

【樣例說明】

  4-2-1-3-6為這棵二叉樹中的一條最長鏈。

【數據規模】

對於10%的數據,有N≤10;

對於40%的數據,有N≤100;

對於50%的數據,有N≤1000;

對於60%的數據,有N≤10000;

對於100%的數據,有N≤100000,且保證了樹的深度不超過32768。

【提示】

關於二叉樹:

二叉樹的遞歸定義:二叉樹要麽為空,要麽由根結點,左子樹,右子樹組成。左子樹和右子樹分別是一棵二叉樹。

請註意,有根樹和二叉樹的三個主要差別:

1. 樹的結點個數至少為1,而二叉樹的結點個數可以為0;

2. 樹中結點的最大度數沒有限制,而二叉樹結點的最大度數為2;

3. 樹的結點無左、右之分,而二叉樹的結點有左、右之分。

關於最長鏈:

最長鏈為這棵二叉樹中一條最長的簡單路徑,即不經過重復結點的一條路徑。可以容易證明,二叉樹中最長鏈的起始、結束結點均為葉子結點。

求了樹的直徑,不過樣例~莫名其妙的A了,可能是數據太水

 1 #include <algorithm>
 2
#include <cstring> 3 #include <cstdio> 4 #include <vector> 5 6 using namespace std; 7 8 const int N(100015); 9 vector<int>vec[N]; 10 int n,lson,rson; 11 int s,t,i,dis[N]; 12 bool vis[N]; 13 14 void DFS(int x) 15 { 16 for(int i=0;i<vec[x].size();i++) 17 if(!dis[vec[x][i]]) dis[vec[x][i]]=dis[x]+1,DFS(vec[x][i]); 18 } 19 20 int main() 21 { 22 scanf("%d",&n); 23 for(i=1;i<=n;i++) 24 { 25 scanf("%d%d",&lson,&rson); 26 if(lson) vec[i].push_back(lson),vec[lson].push_back(i); 27 if(rson) vec[i].push_back(rson),vec[rson].push_back(i); 28 } 29 DFS(1); 30 for(t=i=1;i<=n;i++) if(dis[i]>dis[t]) t=i; 31 memset(dis,0,sizeof(dis)); 32 dis[t]=1; DFS(t); 33 for(s=i=1;i<=n;i++) if(dis[i]>dis[s]) s=i; 34 printf("%d",dis[s]-1); 35 return 0; 36 }

codevs——T1814 最長鏈