P4017 最大食物链计数
题目点这
https://www.luogu.com.cn/problem/P4017
输入输出样例
输入 #1
5 7
1 2
1 3
2 3
3 5
2 5
4 5
3 4
输出 #1
5
说明/提示
各测试点满足以下约定:
【补充说明】
数据中不会出现环,满足生物学的要求。
题目解读
1.食物链有两个点非常特殊
最强者:没人能吃它(出度为0)
最弱者:没人能吃(入度为0)
数食物链的条数就是最弱智到最强者怎么走。
2.链接表存食物链并记录个个入度出度
for(int k=1;k<=b;k++)
{
int c,d;
cin>>c>>d;
add(c,d);
in[d]++;
out[c]++;
}
void add(int a,int b)
{
e[idx]=b;
ne[idx]=h[a];
h[a]=idx++;
}
3.先把每一个入度为0的入队备用
queue <int> r;
for(int k=1;k<=a;k++)
{
if(in[k]==0)
{
r.push(k);
f[k]=1;
}
}
4.bfs搜索
for(int k=h[t];k!=-1;k=n[e])
{
int j=e[k];
f[j]+=f[t];
f[j]%=mod;
in[j]--;//走t的使用完后j入度减一;
if(in[j]==0)
{
if(out[j]==0)
{
ans+=f[j];
ans%=mod;
}
else r.push(j);
}
}
总代码如下
#include<bits/stdc++.h>
using namespace std;
const int N=5e5+5,M=5e3+5,mod=80112002;
int h[M],e[N],ne[N],in[N],out[N],f[M],idx;
int ans;
int a,b;
void add(int a,int b)
{
e[idx]=b;
ne[idx]=h[a];
h[a]=idx++;
}
void bfs(int step)
{
queue <int> r;
for(int k=1;k<=a;k++)
{
if(in[k]==0)
{
r.push(k);
f[k]=1;
}
}
int t;
while(!r.empty())
{
t=r.front();
r.pop();
for(int k=h[t];k!=-1;k=ne[k])
{
int j = e[k];
f[j]+=f[t];
f[j]%=mod;
in[j]--;
if(in[j]==0)
{
if(out[j]==0)
{
ans+=f[j];
ans%=mod;
}
else r.push(j);
}
}
}
}
int main()
{
cin>>a>>b;
memset(h,-1,sizeof(h));
for(int k=1;k<=b;k++)
{
int c,d;
cin>>c>>d;
add(c,d);
in[d]++;
out[c]++;
}
bfs(1);
cout<<ans;
return 0;
}