BZOJ 1194: [HNOI2006]潘多拉的盒子 [DP DFA]

news/2024/7/7 21:56:07

传送门

题意:

s个DFA,选出尽量多的自动机a0, a1, a2, . . . , at,使得a1包含a0、a2包 含a1,以此类推。s ≤ 50。

DFA的字符集为{0,1},有的节点是输出源,节点数n ≤ 50。 


 

判断出包含关系后就是裸的最长路,求$SCC$后$DP$就好了

重点在判断包含:

$n$实在太小了,我们直接枚举所有的自动机,然后两个同时从起点开始$bfs$所有情况看看是否在某个状态一个有输出另一个没有

复杂度$O(n^4)$

注意:

$Candy?$这个沙茶$bfs$没有判断$(0,0)$状态是否一个输出一个不输出$WA$了好久,并且他还有一次求$SCC$没有枚举所有点

#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
typedef long long ll;
const int N=55;
inline int read(){char c=getchar();int x=0,f=1;while(c<'0'||c>'9'){if(c=='-')f=-1;c=getchar();}while(c>='0'&&c<='9'){x=x*10+c-'0';c=getchar();}return x*f;
}
int s,n,m;
struct DFA{int n,m,p[N][2],out[N];
}a[N];
struct edge{int v,ne;
}e[N*N<<1],e2[N*N<<1];
int h[N],cnt,h2[N],cnt2;
inline void ins(int u,int v){//printf("ins %d  %d %d\n",cnt,u,v);cnt++;e[cnt].v=v;e[cnt].ne=h[u];h[u]=cnt;
}
inline void ins2(int u,int v){//printf("ins2 %d %d\n",u,v);edge *e=e2;int *h=h2,&cnt=cnt2;cnt++;e[cnt].v=v;e[cnt].ne=h[u];h[u]=cnt;
}
struct node{int x,y;node(int a=0,int b=0):x(a),y(b){}
}q[N*N];
int head,tail;
bool vis[N][N];
void bfs(DFA &a,DFA &b,int i,int j){int a_b=1,b_a=1;memset(vis,0,sizeof(vis));head=tail=1;q[tail++]=node(0,0);vis[0][0]=1;while(head!=tail){node u=q[head++];int x=u.x , y=u.y;if(a.out[x]&&!b.out[y]) b_a=0;if(!a.out[x]&&b.out[y]) a_b=0;if(a_b==0&&b_a==0) break;for(int i=0;i<=1;i++){int nx=a.p[x][i],ny=b.p[y][i];if(!vis[nx][ny]){vis[nx][ny]=1;q[tail++]=node(nx,ny);}}}if(a_b==1) ins(i,j);else if(b_a==1) ins(j,i);
}
void buildGraph(){for(int i=1;i<=n;i++)for(int j=i+1;j<=n;j++) bfs(a[i],a[j],i,j);
}int dfn[N],dfc,low[N],scc,belong[N];
int st[N],top;
int val[N];
void dfs(int u){dfn[u]=low[u]=++dfc;st[++top]=u;for(int i=h[u];i;i=e[i].ne){int v=e[i].v;if(!dfn[v]){dfs(v);low[u]=min(low[u],low[v]);}else if(!belong[v])low[u]=min(low[u],dfn[v]);}if(dfn[u]==low[u]){scc++;while(true){int x=st[top--];belong[x]=scc;val[scc]++;if(x==u) break;}}
}
int f[N];
int dp(int u,int fa){if(f[u]) return f[u];for(int i=h2[u];i;i=e2[i].ne)if(e2[i].v!=fa) f[u]=max(f[u],dp(e2[i].v,u));return f[u]+=val[u];
}
int main(){//freopen("in","r",stdin);n=read();for(int i=1;i<=n;i++){a[i].n=read();a[i].m=read();for(int j=1;j<=a[i].m;j++) a[i].out[read()]=1;for(int j=0;j<a[i].n;j++) a[i].p[j][0]=read(),a[i].p[j][1]=read();}buildGraph();for(int i=1;i<=n;i++) if(!dfn[i]) dfs(i);for(int u=1;u<=n;u++)for(int i=h[u];i;i=e[i].ne) if(belong[u]!=belong[e[i].v]) ins2(belong[u],belong[e[i].v]);int ans=0;for(int i=1;i<=scc;i++) ans=max(ans,dp(i,0));printf("%d\n",ans);
}

 

 

 


http://lihuaxi.xjx100.cn/news/242810.html

相关文章

RestTemplate的GET多参数请求转发

请求方 RequestMapping(value "/movieFindByUser",method RequestMethod.GET)public Object findByUser(RequestParam(name "name", required false) String name, RequestParam(name "username", required false) String username, Reque…

华为云大数据存储的冗余方式是三副本_大数据入门:HDFS数据副本存放策略

大数据处理当中&#xff0c;数据储存始终是一个重要的环节&#xff0c;从现阶段的市场现状来说&#xff0c;以Hadoop为首的大数据技术框架&#xff0c;仍然占据主流地位&#xff0c;而Hadoop的HDFS&#xff0c;在数据存储方面&#xff0c;仍然得到重用。今天的大数据入门分享&a…

琐碎的知识库

禁止当前 Activity截图 <pre> Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); getWindow().addFlags(WindowManager.LayoutParams.FLAG_SECURE); setContentView(R.layout.activity_main); } </pre> 获取当前…

k均值聚类算法考试例题_一文读懂K-means聚类算法

1、引言什么是聚类&#xff1f;我们通常说&#xff0c;机器学习任务可以分为两类&#xff0c;一类是监督学习&#xff0c;一类是无监督学习。监督学习&#xff1a;训练集有明确标签&#xff0c;监督学习就是寻找问题&#xff08;又称输入、特征、自变量&#xff09;与标签&…

JAVA工资高吗

JAVA工资高吗?很多人都是非常关注这个问题的&#xff0c;近几年&#xff0c;java技术在互联网行业有了自己的一席之地&#xff0c;越来越多的人都投身到java技术行业&#xff0c;下面我们来看看详细的介绍。 JAVA工资高吗? 近年来,在美国、加拿大、澳大利亚、新加坡等发达国家…

http

http请求由3个部分组成 1.请求行&#xff1a; 请求行包括 方法符号&#xff0c;请求的URI和协议的版本    请求 URL: http://www.cnblogs.com/ 请求方法: GET 版本HTTP/1.1 2.请求头 Host: www.cnblogs.com User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x…

VS Code - Debugger for Chrome调试JavaScript的两种方式

VS Code - Debugger for Chrome调试JavaScript的两种方式 最近由于出差的缘故&#xff0c;博客写的不是很多&#xff0c;一直想写一篇VS Code - Debugger for Chrome相关的文章&#xff0c;没想到一直拖到了今天。VS Code 开源以后确实在社区得到了很多人的支持&#xff0c;当中…

SQLDataSet中执行DDL语句

在SQLDataSet中执行我们输入的DDL语句&#xff0c;并观察执行结果。 这里为了省输入的时间&#xff0c;从先输好的记事本中复制的SQL语句。效果图: ************************************************************************************** 具体操作: **********************…