其他分享
首页 > 其他分享> > 9.20 考试

9.20 考试

作者:互联网

第二题题解

首先,一个个联通块内的点一定可以相互到达,所以,可以缩点;
然后就变成了一个有向无环图,之后dfs预处理最大值即可

#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
const int N=2e5+7;
struct edge{
	int v,nxt;
}e[N<<1],e1[N<<1];
int n,m,k,cnt,h,cur,T;
int st[N],dfn[N],low[N],vis[N],id[N],maxn[N],head[N],w[N],head1[N],ans[N],ok[N];
void add_edge(int u,int v){
	e[++cnt]=(edge){v,head[u]};
	head[u]=cnt;
}
void add(int u,int v){
	e1[++cnt]=(edge){v,head1[u]};
	head1[u]=cnt;
}
void tarjan(int u){
	dfn[u]=low[u]=++cnt;
	st[++h]=u;
	vis[u]=1;
	for(int i=head[u];i;i=e[i].nxt){
		int to=e[i].v;
		if(!dfn[to]){
			tarjan(to);
			low[u]=min(low[u],low[to]);
		}else if(vis[to]){
			low[u]=min(low[u],dfn[to]);
		}
	}
	int k;
	if(dfn[u]==low[u]){
		cur++;
		do{
			k=st[h],h--;
			vis[k]=0;
			id[k]=cur;
			maxn[cur]=max(w[k],maxn[cur]);
		}while(u!=k);
	}
}
void dfs(int u){
	int res=maxn[u];
	for(int i=head1[u];i;i=e1[i].nxt){
		int to=e1[i].v;
		if(!ok[to]) dfs(to);
		res=max(ans[to],res);
	}
	ans[u]=res;
	ok[u]=1;
}
int main(){
	freopen("neural.in","r",stdin);
	freopen("neural.out","w",stdout);
	scanf("%d",&T);
	while(T--){
		memset(head,0,sizeof(head));
		memset(vis,0,sizeof(vis));
		memset(id,0,sizeof(id));
		memset(maxn,0,sizeof(maxn));
		memset(dfn,0,sizeof(dfn));
		memset(low,0,sizeof(low));
		memset(head1,0,sizeof(head1));
		memset(ok,0,sizeof(ok));
		cnt=0,h=0;
		scanf("%d%d%d",&n,&m,&k);
		for(int i=1;i<=n;i++){
			scanf("%d",&w[i]);
		}
		for(int i=1;i<=m;i++){
			int x,y;
			scanf("%d%d",&x,&y);
			add_edge(x,y);
		}
		cnt=0;
		cur=0;
		for(int i=1;i<=n;i++) if(!dfn[i]) tarjan(i);
		cnt=0;
		for(int i=1;i<=n;i++){
			for(int j=head[i];j;j=e[j].nxt){
				int to=e[j].v;
				int tx=id[i],ty=id[to];
				if(tx==ty) continue;
				add(tx,ty);
			}
		}
		for(int i=1;i<=cur;i++) if(!ok[i]) dfs(i);
		for(int i=1;i<=k;i++){
			int now,x;
			scanf("%d%d",&now,&x);
			cout<<1LL*ans[id[now]]*x<<"\n";
		}
	}
	fclose(stdin);
	fclose(stdout);
	return 0;
}
/*
3
5 10 5
4 10 8 1 10
1 3
1 4
1 5
1 3
2 1
2 5
4 3
4 3
4 5
5 1
1 4
4 6
1 9
4 7
2 9
5 10 5
2 8 8 10 10
2 1
2 3
3 2
3 4
3 1
3 2
3 4
4 1
5 4
5 1
1 4
2 3
4 7
3 10
1 5
5 10 5
9 9 8 2 1
1 5
1 5
2 1
2 4
2 4
2 4
3 2
3 1
4 3
4 3
5 9
3 9
2 7
5 1
5 4
//
1
5 10 5
9 9 8 2 1
1 5
1 5
2 1
2 4
2 4
2 4
3 2
3 1
4 3
4 3
5 9
3 9
2 7
5 1
5 4
*/

标签:缩点,9.20,int,题解,namespace,dfs,include,考试
来源: https://www.cnblogs.com/Aswert/p/13703529.html