1093: [ZJOI2007]最大半连通子图

Time Limit: 30 Sec  Memory Limit: 162 MB
Submit: 2767  Solved: 1095
[Submit][Status][Discuss]

Description

  一个有向图G=(V,E)称为半连通的(Semi-Connected),如果满足:?u,v∈V,满足u→v或v→u,即对于图中任意
两点u,v,存在一条u到v的有向路径或者从v到u的有向路径。若G'=(V',E')满足V'?V,E'是E中所有跟V'有关的边,
则称G'是G的一个导出子图。若G'是G的导出子图,且G'半连通,则称G'为G的半连通子图。若G'是G所有半连通子图
中包含节点数最多的,则称G'是G的最大半连通子图。给定一个有向图G,请求出G的最大半连通子图拥有的节点数K
,以及不同的最大半连通子图的数目C。由于C可能比较大,仅要求输出C对X的余数。

Input

  第一行包含两个整数N,M,X。N,M分别表示图G的点数与边数,X的意义如上文所述接下来M行,每行两个正整
数a, b,表示一条有向边(a, b)。图中的每个点将编号为1,2,3…N,保证输入中同一个(a,b)不会出现两次。N ≤1
00000, M ≤1000000;对于100%的数据, X ≤10^8

Output

  应包含两行,第一行包含一个整数K。第二行包含整数C Mod X.

Sample Input

6 6 20070603
1 2
2 1
1 3
2 4
5 6
6 4

Sample Output

3
3

HINT

 

Source

——————————————————我是分割线————————————————————
spfa+dp+tarjan

先缩点,重新建图,使其成为一个 DAG,

DAG 中每个点有一个点权表示这个点是原图中的几个点缩成的

新图中的一个最大半连通子图,必然是新图中的一个最长链(点权和最大),

知道了这点之后,DP 就行了,

类似于树形 DP,先求出从每个点出发,能走的最长链是多长,统计最长的那条就是最大半连通子图的点的数量了,

至于怎么求有多少个最大半连通子图,也是一样的 DP 就行,在上一步的 DP 之后,再 DP 一遍,统计每个点出发能走出多少条最长链,最后统计求和即可

 /*
Problem:
OJ:
User: S.B.S.
Time:
Memory:
Length:
*/
#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<queue>
#include<cstdlib>
#include<iomanip>
#include<cassert>
#include<climits>
#include<functional>
#include<bitset>
#include<vector>
#include<list>
#include<map>
#define F(i,j,k) for(int i=j;i<=k;i++)
#define M(a,b) memset(a,b,sizeof(a))
#define FF(i,j,k) for(int i=j;i>=k;i--)
#define BUG system("pause")
#define maxn 200000
#define inf 0x3f3f3f3f
#define maxm 5000000
//#define LOCAL
using namespace std;
int read(){
int x=,f=;char ch=getchar();
while(ch<''||ch>''){if(ch=='-')f=-;ch=getchar();}
while(ch>=''&&ch<=''){x=x*+ch-'';ch=getchar();}
return x*f;
}
int head[maxn],to[maxm],next[maxm];
int dfn[maxn],low[maxn];
int st[maxm],ed[maxm];
int n,m,cnt,ans,anss,mod;
int tot,belong[maxn],t,p,stk[maxn],val[maxn];
bool instk[maxn];
int num[maxn],in[maxn],dp[maxn],q[maxm],vis[maxn];
inline void add(int u,int v)
{
to[cnt]=v;
next[cnt]=head[u];
head[u]=cnt++;
}
inline void init()
{
memset(head,-,sizeof(head));cnt=;
cin>>n>>m>>mod;
for(int i=;i<=m;i++)
{
cin>>st[i]>>ed[i];
add(st[i],ed[i]);
}
}
inline void dfs(int u)
{
low[u]=dfn[u]=++t;
stk[++p]=u; instk[u]=true;
for(int i=head[u];i!=-;i=next[i])
{
if(!dfn[to[i]])
{
dfs(to[i]);
low[u]=min(low[u],low[to[i]]);
}
else if(instk[to[i]]) low[u]=min(low[u],dfn[to[i]]);
}
if(dfn[u]==low[u])
{
tot++;
int tmp=-;
while(tmp!=u)
{
tmp=stk[p--];
belong[tmp]=tot;
val[tot]++;
instk[tmp]=false;
}
}
}
inline void topsort()
{
int h=,t=,u;
for(int i=;i<=tot;i++)
if(in[i]==)
{
q[t++]=i;
dp[i]=val[i];
num[i]=;
}
while(h<t)
{
u=q[h++];
for(int i=head[u];i!=-;i=next[i])
{
in[to[i]]--;
if(in[to[i]]==) q[t++]=to[i];
if(vis[to[i]]==u) continue;
if(dp[to[i]]<dp[u]+val[to[i]])
{
dp[to[i]]=dp[u]+val[to[i]];
num[to[i]]=num[u];
}
else if(dp[to[i]]==dp[u]+val[to[i]])
{
num[to[i]]=(num[to[i]]+num[u])%mod;
}
vis[to[i]]=u;
}
}
}
inline void go()
{
for(int i=;i<=n;i++) if(!dfn[i]) dfs(i);
memset(head,-,sizeof(head));cnt=;
for(int i=;i<=m;i++)
if(belong[st[i]]!=belong[ed[i]])
{
add(belong[st[i]],belong[ed[i]]);
in[belong[ed[i]]]++;
}
topsort();
for(int i=;i<=tot;i++)
{
if(dp[i]>ans)
{
ans=dp[i];
anss=num[i];
}
else if(dp[i]==ans) anss=(anss+num[i])%mod;
}
cout<<ans<<endl<<anss<<endl;
}
int main()
{
std::ios::sync_with_stdio(false);//cout<<setiosflags(ios::fixed)<<setprecision(1)<<y;
#ifdef LOCAL
freopen("data.in","r",stdin);
freopen("data.out","w",stdout);
#endif
init();
go();
return ;
}

BZOJ 1093 最大半连通子图 题解的更多相关文章

  1. bzoj 1093 最大半连通子图 - Tarjan - 拓扑排序 - 动态规划

    一个有向图G=(V,E)称为半连通的(Semi-Connected),如果满足:?u,v∈V,满足u→v或v→u,即对于图中任意两点u,v,存在一条u到v的有向路径或者从v到u的有向路径.若G'=(V ...

  2. [BZOJ]1093 最大半连通子图(ZJOI2007)

    挺有意思的一道图论. Description 一个有向图G=(V,E)称为半连通的(Semi-Connected),如果满足:∀u,v∈V,满足u→v或v→u,即对于图中任意两点u,v,存在一条u到v ...

  3. BZOJ 1093 最大半连通子图

    缩点求最长链. #include<iostream> #include<cstdio> #include<cstring> #include<algorith ...

  4. BZOJ 1093 [ZJOI2007] 最大半连通子图(强联通缩点+DP)

    题目大意 题目是图片形式的,就简要说下题意算了 一个有向图 G=(V, E) 称为半连通的(Semi-Connected),如果满足图中任意两点 u v,存在一条从 u 到 v 的路径或者从 v 到 ...

  5. BZOJ 1093 [ZJOI2007]最大半连通子图

    1093: [ZJOI2007]最大半连通子图 Time Limit: 30 Sec  Memory Limit: 162 MBSubmit: 1986  Solved: 802[Submit][St ...

  6. 最大半连通子图 bzoj 1093

    最大半连通子图 (1.5s 128MB) semi [问题描述] 一个有向图G = (V,E)称为半连通的(Semi-Connected),如果满足:∀ u, v ∈V,满足u->v 或 v - ...

  7. bzoj 1093 [ZJOI2007]最大半连通子图(scc+DP)

    1093: [ZJOI2007]最大半连通子图 Time Limit: 30 Sec  Memory Limit: 162 MBSubmit: 2286  Solved: 897[Submit][St ...

  8. BZOJ 1093: [ZJOI2007]最大半连通子图( tarjan + dp )

    WA了好多次... 先tarjan缩点, 然后题意就是求DAG上的一条最长链. dp(u) = max{dp(v)} + totu, edge(u,v)存在. totu是scc(u)的结点数. 其实就 ...

  9. 【刷题】BZOJ 1093 [ZJOI2007]最大半连通子图

    Description 一个有向图G=(V,E)称为半连通的(Semi-Connected),如果满足:?u,v∈V,满足u→v或v→u,即对于图中任意 两点u,v,存在一条u到v的有向路径或者从v到 ...

随机推荐

  1. oj提交时常见错误归纳

    Presentation Error: 常见的PE错误应该有以下的几种情况: 每行输出之后有空行 每两行输出之间有空行 一行中,每个输出数字(或字符串,等)之间有空格 一行中,每个输出数字(或字符串, ...

  2. CSS html标签元素分类

    在CSS中,html中的标签元素大体被分为三种不同的类型: 块状元素.内联元素(又叫行内元素)和内联块状元素.  常用的块状元素有: <div>.<p>.<h1>… ...

  3. 过滤器中处理multipart/form-data头部的post请求request.getParameter(")获取不到参数问题

    如果不是文件类型请求,我们使用request.getParameter("");方法是可以获取到参数内容的,如果是文件类型的请求即请求的头部信息为“multipart/form-d ...

  4. rsync基础

    参考资料:骏马金龙的rsync系列.该博主的博文质量很好,推荐大家关注. 环境 操作系统:CentOS Linux release 7.5.1804 (Core) 软件:rsync  version ...

  5. 【Ray Tracing The Next Week 超详解】 光线追踪2-2

    Chapter 2:Bounding Volume Hierarchies 今天我们来讲层次包围盒,乍一看比较难,篇幅也多,但是咱们一步一步来,相信大家应该都能听懂 BVH 和 Perlin text ...

  6. 使用JAXB实现Bean与Xml相互转换

    最近几天,我自己负责的应用这边引入了一个新的合作方,主要是我这边调用他们的接口,但是有个很坑的地方,他们传参居然不支持json格式,并且只支持xml格式进行交互,于是自己写了一个工具类去支持bean与 ...

  7. 利用cve-2017-11882的一次渗透测试

    利用工具:https://github.com/Ridter/CVE-2017-11882/ 影响版本: office 2003 office 2007 office 2010 office 2013 ...

  8. Token以及签名signature的设计与实现

    LZ第一次给app写开放接口,把自己处理Token的实现记录下来,目的是如果以后遇到好的实现,能在此基础上改进.这一版写法非常粗糙,写出来就是让大家批评的,多多指教,感谢大家. 当初设计这块想达到的效 ...

  9. Linux/CentOS实现交换机-简单的交换机实现

    个人理解: 1.交换机的核心在于Mac地址学习,使其能在全双工/半双工下进行转发工作. 2.对于专业的交换机来说,使用的是专业的网络芯片并自己实现里面的协议,比如说华为的,为什么能卖那么贵,贵在于网络 ...

  10. MikroTik RouterOS虚拟机/实体机安装方法

    一.设置光驱 二.安装RouerOS 按a全选,按i安装,q退出,空格可以选取或取消选取.这里是选择你要安装的组件. 是否要保存原有配置:是否要提交.一路y. 安装好之后按回车重启:之后为这个界面,安 ...