1. 程式人生 > >NOIp模擬1 Graph

NOIp模擬1 Graph

urn val scan 最大 不能 ext 問題 dfs ems

問題背景

本套模擬題旨在復習各個noip知識點

試題描述

給出 N 個點,M 條邊的有向圖,對於每個點 v,求 A(v) 表示從點 v 出發,能到達的編號最大的點。

輸入格式

第 1 行,2 個整數 N,M。 接下來 M 行,每行 2 個整數 Ui,Vi,表示邊 <Ui,Vi>。點用 1,2,...,N 編號。

輸出格式

N 個整數 A(1),A(2),...,A(N)。

輸入示例

4 3
1 2
2 4
4 3

輸出示例

4 4 3 4

註釋說明

對於 60% 的數據,1 ≤ N,K ≤ 10^3
對於 100% 的數據,1 ≤ N,M ≤ 10^5。

【分析】

這道題的做法應該比較多,這裏選擇記憶化dfs, 還沒試能不能過,先放在這。

註意一個點要是不和其它任意點連通的話,a[i]就是它本身。

【代碼】

 1 #include <bits/stdc++.h>
 2 using namespace std;
 3 
 4 struct State {
 5     int next, to;
 6 }e[200005];
 7 
 8 int n, m, u, v, head[100005], cnt, a[100005];
9 bool vis[100005]; 10 11 void add(int u, int v) { 12 e[++cnt].to=v, e[cnt].next=head[u], head[u]=cnt; 13 } 14 15 void dfs(int s) { 16 if (vis[s]) 17 return; 18 vis[s]=true; 19 for (int i=head[s];i!=-1;i=e[i].next) { 20 dfs(e[i].to); 21 a[s]=max(a[s], max(e[i].to, a[e[i].to]));
22 } 23 return; 24 } 25 26 int main() { 27 memset(head, -1, sizeof(head)); 28 cin >> n >> m; 29 for (int i=1;i<=n;++i) 30 a[i]=i; 31 for (int i=1;i<=m;++i) { 32 scanf("%d %d", &u, &v); 33 add(u, v); 34 } 35 for (int i=1;i<=n;++i) 36 dfs(i); 37 for (int i=1;i<=n;++i) 38 printf("%d ", a[i]); 39 }

NOIp模擬1 Graph