Tarjan shrink point [USACO5.3] Campus Network Network of Schools (Los Valley P2746)

[USACO5.3] Campus Network Network of Schools

Title Description

Some schools even into a computer network. Those schools have entered into an agreement: each school will give some other school distribution software (referred to as "receiving schools"). Note that the list even if the B school in the distribution list A, A is not necessarily in the B-school's.

You want to write a program to calculate, according to the agreement, in order to make the network all schools use the new software, new schools must accept a minimum number of copies of the Software (subtasks A). Furthermore, we wanted to determine through a school to send any new software, which will be distributed to all schools in the network. To accomplish this task, we may have to expand the school to receive lists to new members. Calculate the minimum necessary to increase the number of extensions that make us no matter which school to send new software, it will reach all the remaining schools (subtasks B). An extension is the introduction of a new member in the school receives a school list.

Input Format

The first line of the input file comprises a positive integer N, the number of school network. Schools identified by the first N positive integers.

Next, each line represents a line N school receiving list (distribution list), row i + 1-i includes receiving an identifier of the school school. Each list ends with 0, 0 empty list only one representation.

Output Format

Your program should output two lines in the output file.

The first line should include a positive integer, A solution of subtask FIG.

The second row should contain a non-negative integer, B solution subtask FIG.


This question is the question of comparative template Tarjan shrink points, but the more important point is to understand the DAG to become a strongly connected graph, and to raise the number of sides is the degree of penetration and the number of points is 0 0 the maximum number of points;

Code:

#include<bits/stdc++.h>
#define LL long long
#define pa pair<int,int>
#define ls k<<1
#define rs k<<1|1
#define inf 0x3f3f3f3f
using namespace std;
const int N=20010;
const int M=1000100;
const LL mod=100000000;
int dfn[N],low[N],tot,head[N],cnt,n,sta[N],top,fa[N],in[N],out[N],sum;
vector<int>R[N];
bool vis[N],ma[N][N];
struct Node{
	int to,nex;
}edge[M];
void add(int p,int q){
	edge[cnt].to=q;
	edge[cnt].nex=head[p];
	head[p]=cnt++;
}
void Tarjan(int p){
	dfn[p]=low[p]=++tot;
	if(!vis[p]) vis[p]=true,sta[++top]=p;
	for(int i=head[p];~i;i=edge[i].nex){
		int q=edge[i].to;
		if(!dfn[q]){
			Tarjan(q);
			low[p]=min(low[p],low[q]);
		}
		else if(vis[q]) low[p]=min(low[p],dfn[q]);
	}
	if(dfn[p]==low[p]){
		sum++;//总点数 
		fa[p]=p;
		vis[p]=false;
		while(sta[top]!=p){
			vis[sta[top]]=false;
			fa[sta[top]]=p;
			top--;
		}
		top--;
	}
}
int main(){
	memset(head,-1,sizeof(head));
	cin>>n;
	for(int i=1;i<=n;i++){
		int q;
		while(1){
			scanf("%d",&q);
			if(q==0) break;
			add(i,q);
			R[i].push_back(q);
		}
	}
	for(int i=1;i<=n;i++){
		if(!dfn[i]) Tarjan(i);
	}
	for(int i=1;i<=n;i++){
		for(int j=0;j<R[i].size();j++){
			if(fa[i]!=fa[R[i][j]]&&!ma[fa[i]][fa[R[i][j]]]){
				ma[fa[i]][fa[R[i][j]]]=true;
				in[fa[R[i][j]]]++;
				out[fa[i]]++;
			}
		}
	}
	int ans1=0,ans2=0;
	for(int i=1;i<=n;i++){
		if(fa[i]==i&&in[i]==0) ans1++;
		if(fa[i]==i&&out[i]==0) ans2++;
	}
	if(sum==1) cout<<1<<endl<<0<<endl;
	else cout<<ans1<<endl<<max(ans1,ans2)<<endl;
    return 0;
}
Published 264 original articles · won praise 46 · views 10000 +

Guess you like

Origin blog.csdn.net/qq_44291254/article/details/104967069