Luogu P1470 最长前缀 Longest Prefix

Luogu P1470 最长前缀 Longest Prefix

Portal(传送门)

注释

这道题与上一篇博客的题几乎一样

解析

  • 有点麻烦的地方就是字符串的输入

方法一:类dp

Code

#include<cmath>
#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#define LL long long
using namespace std;
int n,m,l,rot,trie[2005][26];
char x[80],ele[15],seq[1200005];
bool book[2005],vis[1200005];
void insert(char s[])
{
    int u=0,len=strlen(s+1);
    for(int i=1;i<=len;i++)
    {
        int v=s[i]-'A';
        if(!trie[u][v]) trie[u][v]=++rot;
        u=trie[u][v];
    }
    book[u]=1;
    return;
}
int find(char s[],int len)
{
    int u=0,maxl=0;
    memset(vis,0,sizeof(vis));
    for(int i=1;i<=len;i++)
    {
        int v=s[i]-'A';
        if(!trie[u][v]) break;
        u=trie[u][v];
        if(book[u]) vis[i]=1;
    }
    for(int i=1;i<=len;i++)
    {
        if(!vis[i]) continue;
        else maxl=i;
        int u=0;
        for(int j=i+1;j<=len;j++)
        {
            int v=s[j]-'A';
            if(!trie[u][v]) break;
            u=trie[u][v];
            if(book[u]) vis[j]=1;
        }
    }
    return maxl;
}
int main()
{
    while(cin>>(ele+1))
    {
        if(ele[1]=='.') break;
        insert(ele);
    }
    while(cin>>(x+1))
    {
        for(int i=1;i<=strlen(x+1);i++) seq[++l]=x[i];
    }
    printf("%d\n",find(seq,l));
    return 0;
}

方法二:记忆化搜索

#include<cmath>
#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#define LL long long
using namespace std;
int n,m,l,maxl,rot,trie[2005][26];
char x[80],ele[15],seq[1200005];
bool book[2005],vis[1200005];
void insert(char s[])
{
    int u=0,len=strlen(s+1);
    for(int i=1;i<=len;i++)
    {
        int v=s[i]-'A';
        if(!trie[u][v]) trie[u][v]=++rot;
        u=trie[u][v];
    }
    book[u]=1;
    return;
}
void dfs(char s[],int x,int len)
{
    if(vis[x]) return;
    vis[x]=1;
    int u=0,i=x;
    maxl=max(maxl,i-1);
    while(i<=len)
    {
        int v=s[i]-'A';
        if(!trie[u][v]) break;
        u=trie[u][v];
        i++;
        if(book[u]) dfs(s,i,len);
    }
    return;
}
int main()
{
    while(cin>>(ele+1))
    {
        if(ele[1]=='.') break;
        insert(ele);
    }
    while(cin>>(x+1))
    {
        for(int i=1;i<=strlen(x+1);i++) seq[++l]=x[i];
    }
    dfs(seq,1,l);
    printf("%d\n",maxl);
    return 0;
}

原文地址:https://www.cnblogs.com/Hawking-llfz/p/11475130.html

时间: 2024-07-29 07:43:29

Luogu P1470 最长前缀 Longest Prefix的相关文章

洛谷P1470 最长前缀 Longest Prefix

P1470 最长前缀 Longest Prefix 73通过 236提交 题目提供者该用户不存在 标签USACO 难度普及/提高- 提交  讨论  题解 最新讨论 求大神指导,为何错? 题目描述 在生物学中,一些生物的结构是用包含其要素的大写字母序列来表示的.生物学家对于把长的序列分解成较短的序列(即元素)很感兴趣. 如果一个集合 P 中的元素可以通过串联(元素可以重复使用,相当于 Pascal 中的 “+” 运算符)组成一个序列 S ,那么我们认为序列 S 可以分解为 P 中的元素.元素不一定

题解 P1470 【最长前缀 Longest Prefix】

首先看题,题目要求我们求最长匹配的长度,我们不妨如下思考: ? 对于字符串S,我们从第y位开始搜索(保证前y-1位一定可以是匹配) ? 从第y位开始生成字符串,若此时生成的字符串在P中出现过,则证明 ? 此时的字符串可以被匹配到y+i的位置,我们再从y+i+1开始搜索便好了! ? 而问题的答案就是我们已到达的最大的一个y. 那么问题来了,如果按照上述说法搜索,复杂度不稳定,但一定会 ? 超时的,有木有什么优化呢? 答案是有的(不然我写这个题解干什么呢?),我们注意到,如果 ? 对于此时的y,我们

LeetCode 14 Longest Common Prefix 最长前缀

题目:Write a function to find the longest common prefix string amongst an array of strings. 翻译:求一个字符串数组中 共同的最长前缀. 思路:以第一个串为基准,逐个位置遍历,并遍历字符串数组,如果出现某个字符串长度小于当前位置,或者出现当前位置的字符不相同,返回字串strs[0].substring(0,pos):思路很简单. 代码: public String longestCommonPrefix(Str

COGS 696. [IOI1996][USACO 2.3] 最长前缀

★   输入文件:prefix.in   输出文件:prefix.out   简单对比时间限制:1 s   内存限制:128 MB 描述 USACO 2.3.1 IOI96 在生物学中,一些生物的结构是用包含其要素的大写字母序列来表示的.生物学家对于把长的序列分解成较短的序列(即元素)很感兴趣. 如果一个集合 P 中的元素可以通过串联(元素可以重复使用,相当于 Pascal 中的 “+” 运算符)组成一个序列 S ,那么我们认为序列 S 可以分解为 P 中的元素.元素不一定要全部出现(如下例中B

usaco题目分享——Longest Prefix

Longest PrefixIOI'96 The structure of some biological objects is represented by the sequence of their constituents, where each part is denoted by an uppercase letter. Biologists are interested in decomposing a long sequence into shorter sequences cal

USACO Longest Prefix 【水】

用Dp的思想解决了这道题目,也就是所谓的暴力= = 题意:给出一个集合,一个字符串,找出这个字符串的最长前缀,使得前缀可以划分为这个集合中的元素(集合中的元素可以不全部使用). 还不会Trie 树QAQ Source Code: /* ID: wushuai2 PROG: prefix LANG: C++ */ //#pragma comment(linker, "/STACK:16777216") //for c++ Compiler #include <stdio.h>

【USACO 2.3.1】最长前缀

[题目描述] 在生物学中,一些生物的结构是用包含其要素的大写字母序列来表示的.生物学家对于把长的序列分解成较短的序列(即元素)很感兴趣. 如果一个集合 P 中的元素可以通过串联(元素可以重复使用,相当于 Pascal 中的 “+” 运算符)组成一个序列 S ,那么我们认为序列 S 可以分解为 P 中的元素.元素不一定要全部出现(如下例中BBC就没有出现).举个例子,序列 ABABACABAAB 可以分解为下面集合中的元素: {A, AB, BA, CA, BBC} 如果序列S前面K个字符可以由某

kmp(最长前缀与后缀)

http://acm.hdu.edu.cn/showproblem.php?pid=1358 Period Problem Description For each prefix of a given string S with N characters (each character has an ASCII code between 97 and 126, inclusive), we want to know whether the prefix is a periodic string.

Implement Trie and find longest prefix string list

1 package leetcode; 2 3 import java.util.ArrayList; 4 import java.util.List; 5 6 class TrieNode{ 7 Boolean isWord;//true if path till this node represent a string. 8 Integer freq;//numbers of strings share the same prefix 9 Character nodeChar;//chara