题目大意就是 给你一个DAG

然后添加一条边\(x->y\) ,询问以1为根的生成树的个数

QWQ

首先假设没有添加的边

答案就应该是

\[ans=\prod_{i=1}^{n} in[i]
\]

QWQ就相当于每个点选择一个父亲。

那么加入一条边,我们会有一些不合法的情况,那就是包含一条\(y->x\)路径,剩下随便选的方案数。假设全集是\(C\),然后路径上的点的集合是\(S\),那我们实际上求的就是$$\frac{F(C)}{F(S)}$$

其中\(F(S)\)表示\(S\)集合中所有点的入度的乘积

然后对于这个东西,我们可以考虑拓扑图上dp的方式

来解决

//假设我们添加了一条x->y的边,要想不合法,就是求y->x的路径条数
//所以我们要将令起点,也就是y的初值f[y]=ans void addedge(int x,int y)
{
nxt[++cnt]=point[x];
to[cnt]=y;
in[y]++;
point[x]=cnt;
} int qsm(int i,int j)
{
int ans=1;
while (j)
{
if (j&1) ans=ans*i%mod;
i=i*i%mod;
j>>=1;
}
return ans;
} void tpsort()
{
//cout<<ans<<endl;
for (int i=1;i<=n;i++)
{
if (!in[i]) q.push(i);
}
while (!q.empty())
{
int now = q.front();
q.pop();
//cout<<now<<endl;
//int ymh=0;
//if (now==y) ymh=1;
f[now]=f[now]*qsm(d[now],mod-2)%mod; //cout<<now<<" "<<f[now]<<endl;
for (int i=point[now];i;i=nxt[i])
{
int p =to[i];
in[p]--;
f[p]=(f[p]+f[now])%mod;
if (!in[p]) q.push(p);
}
}
}

下面是整个的代码

// luogu-judger-enable-o2
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<cmath>
#include<queue>
#include<map>
#include<set>
#define mk makr_pair
#define ll long long
#define int long long using namespace std; inline int read()
{
int x=0,f=1;char ch=getchar();
while (!isdigit(ch)) {if (ch=='-') f=-1;ch=getchar();}
while (isdigit(ch)) {x=(x<<1)+(x<<3)+ch-'0';ch=getchar();}
return x*f;
} const int maxn = 2e5+1e2;
const int maxm = 2*maxn;
const int mod = 1e9+7; int point[maxn],nxt[maxm],to[maxm];
int n,m;
int cnt,in[maxn];
queue<int> q;
int ans;
int f[maxn];
int x,y;
int d[maxn]; //假设我们添加了一条x->y的边,要想不合法,就是求y->x的路径条数
//所以我们要将令起点,也就是y的初值f[y]=ans void addedge(int x,int y)
{
nxt[++cnt]=point[x];
to[cnt]=y;
in[y]++;
point[x]=cnt;
} int qsm(int i,int j)
{
int ans=1;
while (j)
{
if (j&1) ans=ans*i%mod;
i=i*i%mod;
j>>=1;
}
return ans;
} void tpsort()
{
//cout<<ans<<endl;
for (int i=1;i<=n;i++)
{
if (!in[i]) q.push(i);
}
while (!q.empty())
{
int now = q.front();
q.pop();
//cout<<now<<endl;
//int ymh=0;
//if (now==y) ymh=1;
f[now]=f[now]*qsm(d[now],mod-2)%mod; //cout<<now<<" "<<f[now]<<endl;
for (int i=point[now];i;i=nxt[i])
{
int p =to[i];
in[p]--;
f[p]=(f[p]+f[now])%mod;
if (!in[p]) q.push(p);
}
}
} signed main()
{
n=read(),m=read(),x=read(),y=read();
for (int i=1;i<=m;i++)
{
int u=read(),v=read();
addedge(u,v);
}
ans=1;
for (int i=2;i<=n;i++)
{
if (i==y) ans=ans*(in[i]+1)%mod,d[i]=in[i]+1;
else ans=ans*in[i]%mod,d[i]=in[i];
}
f[y]=ans;
if (x==1)
{
cout<<ans<<"\n";
return 0;
}
tpsort();
cout<<(ans-f[x]+mod)%mod<<endl;
return 0;
}

洛谷3244 落忆枫音 (拓扑图dp+式子)的更多相关文章

  1. 洛谷P3244 落忆枫音 [HNOI2015] 拓扑排序+dp

    正解:拓扑排序+dp 解题报告: 传送门 我好暴躁昂,,,怎么感觉HNOI每年总有那么几道题题面巨长啊,,,语文不好真是太心痛辣QAQ 所以还是要简述一下题意,,,就是说,本来是有一个DAG,然后后来 ...

  2. P3244-[HNOI2015]落忆枫音【dp】

    正题 题目链接:https://www.luogu.com.cn/problem/P3244 题目大意 给出一个\(\text{DAG}\),保证\(1\)可以到达所有点.然后再加入一条边(之后不一定 ...

  3. 【BZOJ4011】【HNOI2015】落忆枫音(动态规划)

    [BZOJ4011][HNOI2015]落忆枫音(动态规划) 题面 BZOJ 洛谷 Description 「恒逸,你相信灵魂的存在吗?」 郭恒逸和姚枫茜漫步在枫音乡的街道上.望着漫天飞舞的红枫,枫茜 ...

  4. 【BZOJ】【4011】【HNOI2015】落忆枫音

    拓扑排序+DP 题解:http://blog.csdn.net/PoPoQQQ/article/details/45194103 http://www.cnblogs.com/mmlz/p/44487 ...

  5. BZOJ 4011: [HNOI2015]落忆枫音( dp )

    DAG上有个环, 先按DAG计数(所有节点入度的乘积), 然后再减去按拓扑序dp求出的不合法方案数(形成环的方案数). ---------------------------------------- ...

  6. bzoj4011[HNOI2015]落忆枫音 dp+容斥(?)

    4011: [HNOI2015]落忆枫音 Time Limit: 10 Sec  Memory Limit: 512 MBSubmit: 1125  Solved: 603[Submit][Statu ...

  7. [HNOI2015]落忆枫音 解题报告

    [HNOI2015]落忆枫音 设每个点入度是\(d_i\),如果不加边,答案是 \[ \prod_{i=2}^nd_i \] 意思是我们给每个点选一个父亲 然后我们加了一条边,最后如果还这么统计,那么 ...

  8. 4011: [HNOI2015]落忆枫音

    4011: [HNOI2015]落忆枫音 链接 分析: 原来是一个DAG,考虑如何构造树形图,显然可以给每个点找一个父节点,所以树形图的个数就是$\prod\limits_u deg[u]$. 那么加 ...

  9. BZOJ 4011 【HNOI2015】 落忆枫音

    题目链接:落忆枫音 以下内容参考PoPoQQQ大爷的博客 首先我们先来考虑一下如果没有新加入的那条边,答案怎么算. 由于这是一个\(DAG\),所以我们给每个点随便选择一条入边,最后一定会构成一个树形 ...

随机推荐

  1. BUUCTF-[网鼎杯 2020 青龙组]AreUSerialz

    BUUCTF-[网鼎杯 2020 青龙组]AreUSerialz 看题 <?php include("flag.php"); highlight_file(__FILE__) ...

  2. docker run命令指定GPU多个显卡不生效的问题解决和代码示例

    问题描述:我有一个程序(app),需要用到显卡来跑.原本的部署方式 是直接修改程序的配置文件来指定要用到的显卡. 这是我服务器的显卡信息:总共3卡 分别是 0卡 ,1卡和2卡. [root@k8s-r ...

  3. python 动图gif合成与分解

    合成 #!/usr/bin/env python3 # -*- coding: utf-8 -*- import os import sys import imageio def main(imgs_ ...

  4. 小程序 读取照片 EXIF 元信息

    安装 exif.js npm install exif-js --save UI <button type="primary" @click="onExif&quo ...

  5. Mysql常用sql语句(10)- is null 空值查询

    测试必备的Mysql常用sql语句系列 https://www.cnblogs.com/poloyy/category/1683347.html 前言 is null是一个关键字来的,用于判断字段的值 ...

  6. JS021. 拦截事件的显式处理与默认动作(Web API: event.preventDefault)

    Web API - event.preventDefault( ) Event 接口的  preventDefault( ) 方法,告诉 user agent :如果此事件没有被显式处理,它默认的动作 ...

  7. PyCharm--帮助文档

    PyCharm官方文档翻译 PyCharm快捷键

  8. python库--tensorflow--scope命名方式

    方法   参数 说明 .name_scope() with...: name 在其下使用Variable, 变量名(V_n)前会被加上'name/...'且相同V_n会自动添加后缀加以区分, 使用ge ...

  9. Spring Boot学习(一)——Spring Boot介绍

    Spring Boot介绍 Spring Boot简介 Spring Boot是由Pivotal团队提供的全新框架,其设计目的是用来简化新Spring应用的初始搭建以及开发过程.该框架使用了特定的方式 ...

  10. Devexpress gridcontrol设置列样式

    <dxg:GridControl.Columns><dxg:GridColumn Header="排名" FieldName="UserRank&quo ...