• 最小表示法


    下面对有用到的概念和符号进行声明:

    最小表示法:将一个周期已知的周期循环字符串,以字典序最小的周期进行表示的方法。

    最小周期:字典序最小的那个周期,用大写字母M表示

    T:代表周期

    循环字符串:即S[i+T]=S[i]

    设S是一循环字符串

    (大家不要把中括号和小括号看混了,两个代表的意义不一样)

    S(i):代表S中以下标i为开始的一个周期。比如S=0123456,则S(0)=0123456,S(1)=1234560,S(2)=2345601,S(3)=3456012,以此类推

    S(i)>S(j):代表S(i)的字典序大于S(j)

    S(i)=S(j):代表S(i)于S(j)的字典序相等,即完全匹配。

    同构字符串:设W,U同构,则存在常数r,使得对应任意的i>=0,有W[i+r]=U[i],即W(r)=U(0)称为W,U间的相位差

    例如:W(0)=111222,U (0)=112221,有W(1)=U(0)。

    性质1:假设W,U两个串是同构循环字符串

    充要条件是存在0 <=p,q<T ,使得W(p)=U(q)=M

    否则,W,U不同构。

    性质2,若有W[i]=U[j],W[i+1]=U[j+1],……w[i+k-1]=U[j+k-1]且W[i+k]<U[j+k]

    则有 W(i+x)<U(j+x)(x=0,1,2,……k-1,k)

    例如

    W=221112,U =112221

    有W[0]=U[2]

       W[1]=U[3]

    且W[2]<U[4]

    所以W(0)=221112<U(2)=222111

          W(1)=211122<U(3)=221112

          W(2)=11122<U(4)=211122

    这里可以得出重要的性质,因为若W,U是同构的则W的表示在U中也是存在的。即存在r使得W(0)=U(r)

    则有

    U(r)<U(2)

    U(r+1)<U(3)

    U(r+2)<U(4)

    所以U(2),U(3),U(4),都不可能是最小表示,我们可以直接跳到U(5),继续匹配

    一,用最小表示法匹配同构字符串的原理

    首先我们先来模拟一下暴力匹配

    假设i<=p,j<=q。W,U是互相同构的周期字符串

    W(i),U(j)的匹配结果:

    1.当匹配到k时失败

      若W[i+k]<U[j+k]

      说明W(i)<U(j)

      这时保持i不变,j++

      同理若W[i+k]>U[j+k]

      说明W(i)>U(j)

      这时保持j不变,i++

      即保持字典序较小的那个不变,

    2,当k=T-1时还是成功

      说明U(i)=W(i)

      即W(i)与U(j)相位差为i-j

      即W[x+i-j]=U[x]

     若直到i,j>=len也没匹配成功过,说明U,W不同构

    这样最坏情况就是,i=p,j=q才匹配成功

    因为W(q)和U(p)是最小周期,所以i,j到了p,q无法在继续前进。现在的问题是如果快速的移动i,j,

    以往我们移动i,j,的方法是暴力枚举,即匹配失败后我们只移动一格,但是效率实在太低了。

    然而如果利于的字典序的话,我们就能让i,j跳起来!,从而在O(n)的时间内完成匹配

    下面我们开始做飞机啦

    不妨假设W(i),和U(j)在下标k处匹配失败(0<=k<=T-1)且W(i)>U(i)

    1.W[i+k]>U[j+k]

    2.W[i+x]=U[j+x] (x=0,1,2……k-1)

    由1,2(即性质2)可得

    W(i+x)>U(j+x) (x=0,1,2……k)

    说明存在比W(i+x)字典序还小的周期

    W(i+x)(x=0,1,2……k)都不是最小周期

    所以i+k<q

    所以i可以放心的移动到i+k+1

    同理当W(i)<U(i)时

    j可以放心的移动到j+k+1

    这样我们实现在不浪费每次匹配的情况下完成了匹配

    即使在结果为i=p,j=q的最坏情况下,也只要匹配p+q+n<3n个字符 。

    现在我们得到了新的流程

    1.当匹配到k时失败

      若W[i+k]<U[j+k]

      说明W(i)<U(j)

      这时保持i不变,j+=k+1

      同理若W[i+k]>U[j+k]

      说明W(i)>U(j)

      这时保持j不变,i+=k+1

      即保持字典序较小的那个不变,

    2,当k=T-1时还是成功

      说明U(i)=W(i)

      即W(i)与U(j)相位差为i-j

      即W[x+i-j]=U[x]

     若直到i,j>=len也没匹配成功过,说明U,W不同构

    //这后面的没写完,不知道啥时候会填坑

    二.求最小表示法

    求最小表示法的关键在于利用性质2,快速排除字典序较大的周期

    设循环字符串S的最小表示为S(q), 0<=q<T

    三,其他应用

    1.求最小周期长度

    2.求最大表示

    3.求最大的表示的最大下标

  • 相关阅读:
    Objective C 代码片段(类别)
    误释放对象
    浏览器内核信息整理
    Oracle VM Virtual 下CentOS不能自动获取IP地址
    git 命令归纳
    马蜂窝 iOS App 启动治理:回归用户体验
    马蜂窝火车票系统服务化改造初探
    让前端监控数据采集更高效
    状态机在马蜂窝机票订单交易系统中的应用与优化实践
    马蜂窝张矗:我对技术团队绩效考核管理的几点思考
  • 原文地址:https://www.cnblogs.com/qswg/p/6206245.html
Copyright © 2020-2023  润新知