E. Test

time limit per test2 seconds

memory limit per test256 megabytes

inputstandard input

outputstandard output

Sometimes it is hard to prepare tests for programming problems. Now Bob is preparing tests to new problem about strings — input data to his problem is one string. Bob has 3 wrong solutions to this problem. The first gives the wrong answer if the input data
contains the substring s1, the second enters an infinite loop if the input data contains the substring s2, and the third requires too much memory if the input data contains the substring s3. Bob wants these solutions to fail single test. What is the minimal
length of test, which couldn't be passed by all three Bob's solutions?





Input

There are exactly 3 lines in the input data. The i-th line contains string si. All the strings are non-empty, consists of lowercase Latin letters, the length of each string doesn't exceed 105.





Output

Output one number — what is minimal length of the string, containing s1, s2 and s3 as substrings.





Examples

input

ab

bc

cd

output

4

input

abacaba

abaaba

x

output

11


这道题目是典型的kmp应用。我们知道kmp是快速判断模式字符串是否在目标字符串中存在。先回顾一下kmp算法:
kmp算法最核心的就是next数组,写这道题目之前又把kmp算法给看了一遍:next数组实际上模式字符串中当前位置前面的字符串前缀和后缀公共的最大长度。这个比较抽象和理论,其实next数组还可以理解成模式字符串的对称程度,对称程度越高,next数组越大。在求解next数组的时候,若前面一个next数,为0,那么说明前面没有对称的,新加的字符如果要对称只可能和第一个字符开始比较。如果next数不为0,说明前面一个字符是有和它对称的,那么去找和他对称的字符的下一个字符,如果相等那么next值就++,如果不相等只能等于0了。
下面是代码实现:
void getNext(string P)
{
int len=P.length();
Next[0]=0;
for(int i=1;i<len;i++)
{
int k=Next[i-1];
while(P[i]!=P[k]&&k!=0)
k=Next[k-1];
if(P[i]==P[k])
Next[i]=k+1;
else
Next[i]=0;
}<pre name="code" class="html">

}


还有一个更加精简的kmp算法

void getnext(string P )
{
int j = -1, i = 0;
int len=P.length();
next[0] = -1;
while(i < len)
{
if(j == -1 ||P[i] == P[j])
{
i++;
j++;
next[i] = j;
}
else
j = next[j];
} }

这个两个求next数组算法虽然求得的next数组不太一样,但是都可以用于kmp。下面给kmp的算法

int kmp(string T,string P)
{
int pLen=P.length();
int tLen=T.length();
int i=0,j=0;
while(i<pLen&&j<tLen)
{
if(i==-1||P[i]==T[j])
i++,j++;
else
i=next[i];
}
if(i>=pLen) return j-pLen+1;
        else  return -1;
</pre>接下来看这道题目:题目实际上是要求两字符串头尾想拼接,也即是头尾重合的最大长度。只需要在kmp的基础上稍加改动即可,下面给出AC代码</div><div class="problem-statement" style="margin:0.5em; padding:0px; line-height:1.5em; font-size:1.4rem"></div><div class="problem-statement" style="margin:0.5em; padding:0px; line-height:1.5em; font-size:1.4rem"><pre name="code" class="html">#include <iostream>
#include <string.h>
#include <string>
#include <algorithm>
#include <stdio.h>
#include <math.h>
#include <stdlib.h>
using namespace std;
#define MAX 100000
int _next[3][MAX+5];
string a[3];
int b[3][3];
int c[3];
void get_next(string P,int pos )
{
int j = -1, i = 0;
int len=P.length();
_next[pos][0] = -1;
while(i < len)
{
if(j == -1 ||P[i] == P[j])
{
i++;
j++;
_next[pos][i] = j;
}
else
j = _next[pos][j];
} }
int kmp(string T,string P,int pos)
{
int pLen=P.length();
int tLen=T.length();
int i=0,j=0;
while(i<pLen&&j<tLen)
{
if(i==-1||P[i]==T[j])
i++,j++;
else
i=_next[pos][i];
}
//cout<<i<<endl;
return i;
} int main()
{
cin>>a[0]>>a[1]>>a[2];
c[0]=a[0].length();c[1]=a[1].length();c[2]=a[2].length();
memset(_next,0,sizeof(_next));
get_next(a[0],0);get_next(a[1],1);get_next(a[2],2);
for(int i=0;i<3;i++)
for(int j=0;j<3;j++)
if(i!=j)
b[i][j]=kmp(a[i],a[j],j);
int ans=0;
for(int i=0;i<3;i++)
{
for(int j=0;j<3;j++)
{
if(i==j)
continue;
for(int k=0;k<3;k++)
{
if(k==i||k==j)
continue;
if(b[i][j]==c[j])
ans=max(ans,b[i][j]+b[i][k]);
else
ans=max(ans,b[i][j]+b[j][k]);
}
}
}
printf("%d\n",c[0]+c[1]+c[2]-ans);
return 0; }





CodeForeces 25E (kmp)的更多相关文章

  1. CodeForces 25E Test KMP

    Description Sometimes it is hard to prepare tests for programming problems. Now Bob is preparing tes ...

  2. codeforeces近日题目小结

    题目源自codeforeces的三场contest contest/1043+1055+1076 目前都是solved 6/7,都差了最后一题 简单题: contest/1043/E: 先不考虑m个限 ...

  3. KMP算法求解

    // KMP.cpp : 定义控制台应用程序的入口点. // #include "stdafx.h" #include<iostream> using namespac ...

  4. 简单有效的kmp算法

    以前看过kmp算法,当时接触后总感觉好深奥啊,抱着数据结构的数啃了一中午,最终才大致看懂,后来提起kmp也只剩下“奥,它是做模式匹配的”这点干货.最近有空,翻出来算法导论看看,原来就是这么简单(先不说 ...

  5. KMP算法

    KMP算法是字符串模式匹配当中最经典的算法,原来大二学数据结构的有讲,但是当时只是记住了原理,但不知道代码实现,今天终于是完成了KMP的代码实现.原理KMP的原理其实很简单,给定一个字符串和一个模式串 ...

  6. 萌新笔记——用KMP算法与Trie字典树实现屏蔽敏感词(UTF-8编码)

    前几天写好了字典,又刚好重温了KMP算法,恰逢遇到朋友吐槽最近被和谐的词越来越多了,于是突发奇想,想要自己实现一下敏感词屏蔽. 基本敏感词的屏蔽说起来很简单,只要把字符串中的敏感词替换成"* ...

  7. [KMP]【学习笔记】

    Oulipo Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 36916   Accepted: 14904 Descript ...

  8. KMP算法实现

    链接:http://blog.csdn.net/joylnwang/article/details/6778316 KMP算法是一种很经典的字符串匹配算法,链接中的讲解已经是很明确得了,自己按照其讲解 ...

  9. KMP专题

    1.[HDU 3336]Count the string(KMP+dp) 题意:求给定字符串含前缀的数量,如输入字符串abab,前缀是a.ab.aba.abab,在原字符串中出现的次数分别是2.2.1 ...

随机推荐

  1. nodejs基础 -- EventEmitter

    var events = require('events'); nodejs所有的异步I/O操作在完成时都会发送一个事件到事件队列 nodejs里面的许多对象都会分发事件,如: 一个net.Serve ...

  2. VS2010属性表的建立与灵活运用

    问题引入:在VS2010当中,进行opencv.QT等的编程时,总是需要配置很多属性还有依赖项等,为了减少每次都重复配置属性的工作量,现在可以运行属性表这个东西来简化配置.opencv也可以这样建立使 ...

  3. mysql中,root用户密码被遗忘,该如何进行重置?

    需求描述: 在mysql的测试环境中,有时候会遇到一段时间之后root用户的密码被遗忘的情况, 这个时候,就是需要对root密码进行重置,不过,在生产环境中,这种情况还是很少见. 环境描述: 操作系统 ...

  4. 浅谈无缓存I/O操作和标准I/O文件操作差别

    首先,先略微了解系统调用的概念:        系统调用,英文名system call,每一个操作系统都在内核里有一些内建的函数库,这些函数能够用来完毕一些系统系统调用把应用程序的请求传给内核,调用对 ...

  5. RF-template使用

    在测试案例中,可以使用template设置进行数据驱动的测试,template设置方法: 在设置项中填写模板的关键字名称,测试案例本身只能包含template关键字使用的数据: *** Setting ...

  6. docker学习-运行第一个docker镜像hello world

    docker pull  [OPTIONS] NAME[:TAG]:从远程仓库拉取一个镜像到本地,NAME是要拉取的镜像的名称,TAG是docker镜像的版本,不指定的话默认是最新版本 docker ...

  7. 基于麒麟座开发板2.0的MQTT实现例程

    链接--->https://sanwen8.cn/p/649shZ1.html OneNET现已全面适配标准MQTT协议,相信这一功能的增加会**便于开发者进行设备的接入. OneNET提供了M ...

  8. M0 M4之UART初始化

    新唐的M0/M4 UART都有16级或者64级FIFO,用来缓存UART数据的收/发.例如:如果RX FIFO中断触发级别设为14,UART接收14个字节才会发生RDA(接收数据可得)中断.这样可以降 ...

  9. NUC131的系统管理

    系统复位系统复位可以由如下的任何一种中断实现,这些复位中断标志可以通过寄存器RSTSRC读取. 上电复位 nRESET引脚低电平复位 看门狗复位 低压复位 欠压检测器复位 CPU 复位 ...

  10. Solr4.0+IKAnalyzer中文分词安装

    1.依赖: JDK1.6,Tomcat 5.5,Solr 4.0.0,IKAnalyzer 2012FF Tomcat虽然不是必须,但觉得上生产环境的话,还是得用Tomcat,便于统一管理和监控. T ...