【学习笔记】最小表示法

  • 用途

            给定一个长度为n,可旋转的字符串环,求从哪个位置断开的长度为n的字符串字典序最小/大(以最小为例,最大同理)  

  • 算法描述

    •      令i=0,j=1表示最小的字符串可能的位置;
    •      找到一个k使得s[i+1]==s[j+1],s[i+2]==s[j+2] ,..., s[i+k-1]==s[j+k-1] ;
    •      但是s[i+k]!=s[j+k];
    •      如果此时s[i+k]<s[j+k],对于j' = j + 1 到 j + k 的位置一定不是最优解,因为i+j'-j位置的串一定比j'位置的更优且如果i+j'-j       位置的串更优一定会被i选到,那么就j=j+k+1
    •     s[i+k]>s[j+k]就i=i+k+1,注意i==j时要再向后移动一位
  • 复杂度 

    •  每多匹配一位k,i或j移动的次数就会相应多一位,所以O(n)
  • bzoj1398 Vijos1382寻找主人 Necklace
     1 #include<cstdio>
     2 #include<iostream>
     3 #include<algorithm>
     4 #include<cstring>
     5 #include<queue>
     6 #include<cmath>
     7 #include<vector>
     8 #include<stack>
     9 #include<map>
    10 #include<set>
    11 #define Run(i,l,r) for(int i=l;i<=r;i++)
    12 #define Don(i,l,r) for(int i=l;i>=r;i--)
    13 #define ll long long
    14 #define ld long double
    15 #define inf 0x3f3f3f3f
    16 #define mk make_pair
    17 #define fir first
    18 #define sec second
    19 #define il inline
    20 #define rg register
    21 #define pb push_back
    22 using namespace std;
    23 const int N=2000010;
    24 int n;
    25 char s[N],t[N];
    26 int cal(char *S){
    27     int i= 0, j = 1 ,k;
    28     while(i<n&&j<n){
    29         for(k=0;S[i+k]==S[j+k];k++);
    30         if(S[i+k]<S[j+k]){j+=k+1;if(i==j)j++;}
    31         else {i+=k+1;if(i==j)i++;}
    32     }
    33     return min(i,j);
    34 }
    35 int main(){
    36     freopen("bzoj1398.in","r",stdin);
    37     freopen("bzoj1398.out","w",stdout);
    38     scanf("%s%s",s,t);
    39     n = strlen(s);
    40     for(rg int i=0;i<n;i++)s[i+n] = s[i] , t[i+n] = t[i];
    41     int pos1 = cal(s);
    42     int pos2 = cal(t);
    43     int fg=1;
    44     for(rg int i=0;i<n;i++){
    45         if(s[pos1+i]!=t[pos2+i]){fg=0;break;}
    46     }
    47     if(!fg){puts("No");}
    48     else {
    49         puts("Yes");
    50         for(rg int i=0;i<n;i++){
    51             putchar(s[pos1+i]);
    52         }
    53     }
    54     return 0;
    55 }//by tkys_Austin;
    bzoj1398

猜你喜欢

转载自www.cnblogs.com/Paul-Guderian/p/10206362.html
今日推荐