mulu
感觉难度还是很高的,膜拜大佬们
具体题目
题目解法
难啊,自己开始看到这道题直接上头了,因为题目的样子实在是,哎……所以开始搞暴力,因为自己也不会啊。先是这道第一题,发现可以满分???
拓扑&&BFS?
不知道,但是自己比赛的时候只开始了
D
F
S
DFS
DFS。
然后一大堆迷惑操作,还是大样例太水了,所以过了。
这时候,比赛开始一个小时了。看了看捋了捋自己的做法:因为看到数据上面说每个排水点中转站总数是不会超过10个的,所以开始从每一个排水点开始递归,发现问题严重啊。
开始乱改:
#include<ctime>
#include<cmath>
#include<cstdio>
#include<cstdlib>
#include<cstring>
//#include<bits/stdc++.h>
using namespace std;
long long n,m;
_int128 arr,d[5005],ans[5005][5005];
bool bz[5005][5005],bj[5005];
long long pc[5005],add[5005];
void dg(long long root,long long x,long long y)
{
if(add[x]==true)
{
ans[root][++ans[root][0]]=y;
return ;
}
for(long long i=1;i<=n;++i)
if(bz[i][x]==true)
dg(root,i,y*d[i]);
}
long long gcd(long long x,long long y)
{
if(x<y){long long t=x;x=y,y=t;}
if(x%y==0) return y;
return gcd(y,x%y);
}
int main()
{
memset(bz,false,sizeof(bz));
memset(bj,false,sizeof(bj));
scanf("%lld%lld",&n,&m);
bool bj[3005];
for(long long i=1;i<=n;++i)
{
scanf("%lld",&d[i]);
for(long long j=1;j<=d[i];++j)
{
scanf("%lld",&arr);
bz[i][arr]=true;
bj[arr]=true;
}
if(d[i]==0) pc[++pc[0]]=i;
}
for(long long i=1;i<=n;++i)
if(bj[i]==false)
add[i]=true;
for(long long i=1;i<=pc[0];++i)
dg(pc[i],pc[i],1);
for(long long i=1;i<=n;++i)
if(ans[i][0]>0)
{
long long sum=ans[i][1],kk,sum2=0;
for(long long j=2;j<=ans[i][0];++j)
{
kk=gcd(sum,ans[i][j]);
sum*=ans[i][j]/kk;
}
for(long long j=1;j<=ans[i][0];++j)
sum2+=sum/ans[i][j];
kk=gcd(sum2,sum);
printf("%lld %lld\n",sum2/kk,sum/kk);
}
return 0;
}