2412. Clock Tree

2412. Clock Tree

(File IO): input:clocktree.in output:clocktree.out
時間限制: 1000 ms 空間限制: 262144 KB 具體限制
Goto ProblemSet


題目描述

Farmer John 的新牛棚的設計十分奇怪:它由編號爲 1…N 的 N 間房間(2≤N≤2500),以及 N−1 條走廊組成。每條走廊連接兩間房間,使得每間房間都可以沿着一些走廊到達任意其他房間。
牛棚裏的每間房間都裝有一個在錶盤上印有標準的整數 1…12 的圓形時鐘。然而,這些時鐘只有一根指針,並且總是直接指向錶盤上的某個數字(它從不指向兩個數字之間)。
奶牛 Bessie 想要同步牛棚中的所有時鐘,使它們都指向整數 12。然而,她頭腦稍有些簡單,當她在牛棚裏行走的時候,每次她進入一間房間,她將房間裏的時鐘的指針向後撥動一個位置。例如,如果原來時鐘指向 5,現在它會指向 6,如果原來時鐘指向 12,現在它會指向 1。如果 Bessie 進入同一間房間多次,她每次進入都會撥動這間房間的時鐘。
請求出 Bessie 可能的出發房間數量,使得她可以在牛棚中走動並使所有時鐘指向 12。注意 Bessie 並不撥動她出發房間的時鐘,但任意時刻她再次進入的時候會撥動它。時鐘不會自己走動;時鐘只會在 Bessie 進入時被撥動。此外,Bessie 一旦進入了一條走廊,她必須到達走廊的另一端(不允許走到一半折回原來的房間)。

輸入

輸入的第一行包含 N。下一行包含 N 個整數,均在範圍 1…12 之內,表示每間房間初始時的時鐘設置。以下 N−1 行每行用兩個整數 a 和 b 描述了一條走廊,兩數均在範圍 1…N 之內,爲該走廊連接的兩間房間的編號。

輸出

輸出出發房間的數量,使得 Bessie 有可能使所有時鐘指向 12。

樣例輸入

4
11 10 11 11
1 2
2 3
2 4

樣例輸出

1

數據範圍限制
測試點 1-7 滿足 N≤100。
測試點 8-15 沒有額外限制。

提示
在這個例子中,當且僅當 Bessie 從房間 2 出發時她可以使所有房間的時鐘指向 12(比如,移動到房間 1,2,3,2,最後到 4)。

題目思路:
這道題我們可以每次去枚舉一個房間(i)作爲根,並去更新與它相連的房間。既然題目中是驗證是否能完成,我們不妨貪心地看,每次不停地從父子之間來回走,直到把孩子改成12,這時候根據父子差固定,我們就能知道u現在是多少。然後再去搞下一個孩子,再確定u的值。直到把所有孩子都改好,此時u固定到了某個數。回到上一層,再由父親把u改成12
那麼這麼一輪下來,最後除了根,其他點都是12了。那麼根如果正好是12,說明是可以的。如果根不是12呢?其實根是1也行,因爲這樣就最後的時候從根的最後一個孩子停下,不走回來。這時候根和最後一個孩子的時間會差一個。除了這兩種情況,其他都不行。
if(edge[i].y==v) continue;
一定要加這一句,否則會死循環
因爲:題目規定兩兩房間之間是雙向邊,所以對於任意一個點,它的兒子也是它的爸爸,但是我們規定了只由一個點當根!!

#include<cstdio>
#include<iostream>
#include<cmath>
#include<cstring>
#include<string>
#include<algorithm>
#define fre(x) freopen(#x".in","r",stdin),freopen(#x".out","w",stdout);
using namespace std;
const int MAX=2147483647;
const int N=5020;
struct node
{
	int x,y,next;
} edge[N];
int head[N],tot,a[N],t[N];
void add(int xx,int yy)
{
	edge[++tot].x=xx;
	edge[tot].y=yy;
	edge[tot].next=head[xx];
	head[xx]=tot;
}
void dfs(int u,int v)
{
	for(int i=head[u];i;i=edge[i].next)
	{
		if(edge[i].y==v) continue; 
		dfs(edge[i].y,u);
		t[u]=(t[u]-t[edge[i].y]+12)%12;
	}	
}
int main()
{
	//fre(clocktree);
	int n,u,v,ans=0;
	scanf("%d",&n);
	for(int i=1;i<=n;i++) scanf("%d",&a[i]),a[i]%=12;
	for(int i=1;i<n;i++)
	{
		scanf("%d%d",&u,&v);
		add(u,v),add(v,u);
	}
	for(int i=1;i<=n;i++)
	{
		memcpy(t,a,sizeof(t));
		dfs(i,0);
		if(!t[i]||t[i]==1) ans++;
	}
	printf("%d\n",ans);
	return 0;
}

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章