CF822E,巧妙的字符串DP

传送门
考场上强攻了42分钟终究以失败告终早。知这样就早点去抢hack了,我的房间里T3有个后来fst的,赛场上我看出其问题所在,结果我的hack一直格式错误,气都气死了再给我30s就好了
这题感觉很巧妙,像我这种蒟蒻只想出题解中给出的第一种DP。但出题人却用了点特技(自己看看题解就知道了),目瞪口呆.jpg,真是妙不可言啊

#include<bits/stdc++.h>
typedef long long ll;
const int N=100010;
const ll mo=1000000007;
int n,x,i,l,r,m,mid,g[N][35],j,k;
ll hs[N],ht[N],q[N];
char s[N],t[N];
inline ll hashs(int l,int r){
    return (hs[r]-hs[l-1]*q[r-l+1]%mo+mo)%mo;
}
inline ll hasht(int l,int r){
    return (ht[r]-ht[l-1]*q[r-l+1]%mo+mo)%mo;
}
inline int lcp(int i,int j){
    if(s[i]!=t[j])return 0;
    l=1;
    if(m-j<n-i)r=m-j+1;
        else r=n-i+1;
    while(l<r){
        mid=(l+r+1)>>1;
        if(hashs(i,i+mid-1)==hasht(j,j+mid-1))l=mid;
            else r=mid-1;
    }
    return l;
}
inline void up(int&a,int b){
    if(a<b)a=b;
}
int main(){
    scanf("%d%s%d%s%d",&n,s+1,&m,t+1,&x);
    q[0]=1;
    for(i=1;i<=n;++i){
        q[i]=q[i-1]*31%mo;
        hs[i]=(hs[i-1]*31+s[i]-'a')%mo;
        ht[i]=(ht[i-1]*31+t[i]-'a')%mo;
    }
    i=lcp(1,1);
    g[lcp(1,1)][1]=i;
    for(i=0;i<n;++i)
        for(j=0;j<=x;++j){
            up(g[i+1][j],g[i][j]);
            if(g[i][j]<m)k=lcp(i+1,g[i][j]+1),up(g[i+k][j+1],g[i][j]+k);
                //else return puts("YES"),0;
        }
    for(i=0;i<=x;++i)if(g[n][i]==m)return puts("YES"),0;
    return puts("NO"),0;
}
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值