zoukankan      html  css  js  c++  java
  • 解题:POI 2006 Periods of Words

    题面

    洛谷翻译有毒系列

    正常人能看懂的题面:若$S$可以通过前缀$s$重复若干次(可重叠)来表示($s!=S$),则称$s$是$S$的一个循环串。求一个字符串所有前缀(包括本身)的最长循环串的长度之和。

    根据$nxt$数组的定义,显然每个串的答案是$len-nxt'$,这里的$nxt'$表示最小的前缀=后缀,当$nxt=0$时没有贡献,然后我们可以每次向前跳$nxt$,记忆化之后就是$O(n)$的

     1 #include<cstdio>
     2 #include<cstring>
     3 #include<algorithm>
     4 using namespace std;
     5 const int N=1e6+6;
     6 int nxt[N],pro[N];
     7 long long n,p,ans;
     8 char ss[N];
     9 int main ()
    10 {
    11     scanf("%lld%s",&n,ss);
    12     for(int i=1;i<n;i++)
    13     {
    14         while(p&&ss[i]!=ss[p]) p=nxt[p];
    15         nxt[i+1]=(ss[i]==ss[p])?++p:0;
    16     }
    17     for(int i=1;i<=n;i++)
    18         pro[i]=nxt[i]?pro[nxt[i]]:i,ans+=i-pro[i];
    19     printf("%lld",ans);
    20     return 0;
    21 }
    View Code
  • 相关阅读:
    sklearn库学习笔记1——preprocessing库
    juypter notetbook
    信用卡欺诈
    matplotlib1
    python一行输入多个数
    pandas数据预处理
    pandas基础用法
    numpy简单用法2
    numpy 简单用法
    简单循环
  • 原文地址:https://www.cnblogs.com/ydnhaha/p/9741527.html
Copyright © 2011-2022 走看看