`
darren_nizna
  • 浏览: 72569 次
  • 性别: Icon_minigender_1
  • 来自: 长沙
社区版块
存档分类
最新评论

[ZOJ/ZJU][3190][Resource Archiver][AC自动机]

 
阅读更多

给你 n 个串,和 m 个病毒串。要把这 n 个串连起来来,可以重叠,但不能包含 m 个病毒串中的任意一个。求把 n 个串连起来的最小长度。

#include <iostream>
#include <bitset>
#include <cstdio>
#include <cstdlib>
#include <queue>
using namespace std;

int const N= 1010, M= 60010;
int n, m, cnt, bit[15];
char str[N];

struct Trie{
	int next[2];
	int fail, end;
	
	void init(){
		fail= -1; end= 0;
		next[0]= 0; next[1]= 0;
	}
}tb[M];

inline void insert( char* s, int d ){
	int rt= 0;
	while(  *s ){
		int t= *s- '0';
		
		if( tb[rt].next[t]== 0 ){
			tb[++cnt].init();
			tb[rt].next[t]= cnt;
		}
		rt= tb[rt].next[t]; s++;
	}
	tb[rt].end= d;
}

int que[M], head, tail;

void bfs(){
	int q, p;
	head= 0, tail= 0; que[0]= 0;
	
	while( head<= tail ){
		int now= que[head++];
		
		for( int t= 0; t< 2; ++t )
		if( tb[now].next[t] ){
			p= tb[now].next[t]; q= tb[now].fail;
			
			while( q!= -1 && !tb[q].next[t] ) q= tb[q].fail;
			if( q== -1 ) tb[p].fail= 0;
			else tb[p].fail= tb[q].next[t];
			
			que[++tail]= p;
		}
		else{
			q= tb[now].fail;
			while( q!= -1 && !tb[q].next[t] ) q= tb[q].fail;
			if( q== -1 ) tb[now].next[t]= 0;
			else tb[now].next[t]= tb[q].next[t];
		}
	}
}

struct Node{
	int steps, state, node;
	Node(){}
	Node( int x, int y, int z ):
		node( x ), steps(y), state(z) {}
};

bitset<(1<<10)> flag[M];

int solve(){
	queue<Node> q; q.push( Node(0,0,0) );
	
	flag[0][0]= 1;
	while( !q.empty() ){
		Node now= q.front(); q.pop();
		
		for( int t= 0; t< 2; ++t )
		if( tb[ tb[ now.node ].next[t] ].end>= 0 ){
			Node tmp= now;
			
			tmp.node= tb[ now.node ].next[t];
			tmp.steps+= 1;
			
			if( tb[ tmp.node ].end> 0 )
			tmp.state|= bit[ tb[tmp.node].end- 1 ];
			
			if( tmp.state== bit[n]- 1 ) return tmp.steps;
			
			if( flag[ tmp.node ][ tmp.state ] ) continue;
			flag[ tmp.node ][ tmp.state ]= 1;
			
			q.push( tmp );
		}
	}
	
	return -1;
}

int main(){
	for( int i= 0; i<= 10; ++i ) bit[i]= 1<<i;
	
	while( scanf("%d%d",&n,&m)!= EOF ){
		if( n== 0 && m== 0 ) return 0;
		cnt= 0; tb[0].init();
		
		for( int i= 1; i<= n; ++i ){
			scanf("%s", str );
			insert( str, i );
		}
		
		for( int i= 1; i<= m; ++i ){
			scanf("%s", str );
			insert( str, -1 );
		}
		
		bfs();
		for( int i= 0; i<= cnt; ++i ) flag[i].reset();
		
		int ans= 0;
		ans= solve();
		printf("%d\n", ans );
	}
	
	return 0;
}
 
分享到:
评论

相关推荐

    ZJU/zoj 题库上的部分题源码

    【标题】"ZJU/zoj 题库上的部分题源码"涉及的知识点主要集中在ACM(国际大学生程序设计竞赛)编程领域,尤其是浙江大学(ZJU)ZOJ(Zhejiang University Online Judge)题库中的题目解决方案。ZOJ是一个在线编程评测...

    acm新手必备 浙大acm解答 代码库 zoj zju

    【标题】"acm新手必备 浙大acm解答 代码库 zoj zju" 提供的信息表明,这个压缩包包含的是ACM竞赛相关的代码,主要来自浙江大学(Zhejiang University,简称ZJU)的在线算法竞赛平台ZOJ(Zhejiang Online Judge)。...

    zoj 1140-zju 2433 简单题的部分答案

    标题 "zoj 1140-zju 2433 简单题的部分答案" 暗示了这是一个关于编程竞赛题目的解答集合,其中涵盖了ZOJ(浙江大学在线评测系统)上的两道题目——ZOJ 1140 和 ZJU 2433。这些题目可能属于算法或数据结构的范畴,...

    浙大zoj月赛解题报告及代码

    同时,“浙大 zoj zju acm初学者必备 代码”指出这是一份适合初学者的学习资料,其中的代码实例能够帮助他们熟悉ACM竞赛的编程实践,了解如何在ZOJ平台上进行有效的编程和调试。 【标签】进一步强调了资源的主要...

    Zoj 1005我的解答已经AC

    标题“Zoj 1005我的解答已经AC”表明这是一个关于在线编程竞赛ZOJ(Zhejiang Online Judge)的问题,且提交的解决方案已经通过了所有测试用例(Accepted,简称AC)。ZOJ是一个用于练习和评测算法能力的平台,其中的...

    zoj1951的AC代码

    本代码是zoj上AC的1951的代码,把双重循环简化为O(n),不过素数判断的改进还不够

    zoj 1002_zoj1002_

    【标题】"ZOJ 1002" 是一个在线编程竞赛题目,源自ZOJ(Zhejiang Online Judge),这是一个面向ACM/ICPC(国际大学生程序设计竞赛)的在线评测系统。题目编号1002,通常表示该题是ZOJ平台上的一个问题,可能涉及算法...

    Zoj acm的AC解题报告

    【标题】"Zoj ACM的AC解题报告"揭示了关于在线判题系统ZOJ(Zhejiang University Online Judge)以及ACM(国际大学生程序设计竞赛)的相关知识。ZOJ是中国浙江大学主办的一个在线编程竞赛平台,它为参赛者提供了一个...

    zju700代码 浙大oj代码

    【标题】"zju700代码 浙大oj代码" 涉及的主要知识点是浙江大学(Zhejiang University,简称ZJU)在线评测系统ZOJ(Zhejiang Online Judge)中的编程题目解决方案。ZOJ是为ACM/ICPC(国际大学生程序设计竞赛)训练而...

    zju1001-1399的数据

    4. **字符串处理**:KMP算法、Rabin-Karp算法、Boyer-Moore算法、后缀数组、AC自动机等。 5. **网络流**:最大流、最小割等。 6. **编码解码**:位操作、Base64编码、ASCII编码等。 7. **计算几何**:点线面的...

    zoj 源码700题

    【标题】"zoj 源码700题"是指一个包含700多道ZOJ(在线判题系统Zhejiang Online Judge)编程竞赛题目的源代码集合。这个资源对于学习算法、提高编程技能以及准备编程竞赛的学员来说极具价值。 【描述】"包含了zoj...

    zoj_ac.rar_zoj_zoj 1023_zoj 2792_zoj21_zoj2182

    最近在acm.zju.edu.cn上通过的题目的代码,都是比较有价值的题目

    zoj.gz_ ZOJ_ZOJ 1016_max flow_zoj 1045_zoj.rar

    标题中的"ZOJ.gz_ ZOJ_ZOJ 1016_max flow_zoj 1045_zoj.rar" 提到了两个ZOJ(Zhejiang Online Judge)的题目,分别是1016和1045,这两个数字通常代表在线编程竞赛中的题目编号。这些题目通常涉及到算法和数据结构的...

    zoj 分类加题解(浙大ACM)

    《ZOJ ACM分类加题解》是针对浙江大学ACM竞赛训练平台的一份宝贵资源,它包含了大量的编程竞赛题目和相应的解答。这份资料旨在帮助参赛者提升算法能力,提高解决实际问题的技巧,无论是在无网络环境下还是有网络时,...

    ZOJ:浙江大学程序在线评测系统.docx

    ZOJ,全称“浙江大学程序在线评测系统”(Zhejiang University Online Judge),是一个提供信息学(算法竞赛)题库及程序评测的网站。以下是关于ZOJ的详细介绍: 一、基本信息 名称:浙江大学程序在线评测系统(ZOJ)...

    ZOJ月赛 题解 (ZOJ Monthly, August 2014)

    **ZOJ月赛题解 (ZOJ Monthly, August 2014)** ZOJ(Zhejiang Online Judge)是中国著名的在线编程竞赛平台之一,它为程序员和学生提供了丰富的算法练习和比赛机会。2014年8月的ZOJ月赛是一场面向广大编程爱好者的...

    浙江大学ZOJ题目分类

    浙江大学ZOJ(Zhejiang University Online Judge)是一个在线编程练习平台,主要服务于计算机科学和技术的学习者,特别是对算法和编程有浓厚兴趣的学生。这个平台提供了大量的编程题目,涵盖了各种难度和主题,帮助...

    zju.rar_ZJU_zju.rar_zju2104.cpp

    【标题】"zju.rar_ZJU_zju.rar_zju2104.cpp" 提供的信息显示,这可能是一个与浙江大学(Zhejiang University,简称ZJU)相关的编程资源包。"zju2104.cpp" 文件名暗示这可能是针对浙大某次课程或竞赛的C++代码,编号...

    Problem Arrangement zoj 3777

    Problem Arrangement zoj 3777

    zoj1027解题指南

    【标题】"ZOJ1027解题指南"是一个针对特定编程竞赛题目——ZOJ1027的解决方案集合。ZOJ,全称为“Zhejiang Online Judge”,是浙江大学主办的一个在线编程竞赛平台,提供了丰富的算法题目供参赛者练习和挑战。本解题...

Global site tag (gtag.js) - Google Analytics