SCOI2007压缩

Posted shxnb666

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了SCOI2007压缩相关的知识,希望对你有一定的参考价值。

题面

https://www.luogu.org/problem/P2470

题解

// luogu-judger-enable-o2
#include<cstdio>
#include<iostream>
#include<cstring>
#define ri register int
#define N 55
#define uLL unsigned long long
#define INF 107
using namespace std;
int f[N][N],n;
char s[N];
const uLL p=107;
uLL pp[N];

struct hash
  uLL sum[N];
  void init() 
    sum[0]=0;
    for (ri i=1;i<=n;i++) sum[i]=sum[i-1]*p+s[i]-a;
  
  uLL getval(int l,int r)
    return sum[r]-sum[l-1]*pp[r-l+1];
  
 H;

int dfs(int x,int y)
  if (x==0 && y==0) return 0;
  if (f[x][y]!=INF) return f[x][y];

  int &ret=f[x][y];
  if (x==y) 
    for (ri i=0;i<y;i++) if (dfs(x,i)+1<ret) ret=dfs(x,i)+1;
    return ret;
  

  if (x-1>=y) ret=min(ret,dfs(x-1,y)+1);
  else for (ri i=0;i<y;i++) if (dfs(x,i)+1<ret) ret=dfs(x,i)+1;
  
  int nn=1;
  for (ri i=x-1;i>y;i--) 
    while (i+((1<<nn)-1)*(i-y)<x) nn++;
    if (i+((1<<nn)-1)*(i-y)==x) 
      bool can=1;
      int curr=x;
      while (curr!=i) 
        curr-=(i-y);
        if (H.getval(curr-(i-y)+1,curr)!=H.getval(x-(i-y)+1,x)) can=0;
      
      if (can) ret=min(dfs(i,y)+nn,ret);
    
  
  return ret;


int main()
  pp[0]=1;
  for (ri i=1;i<N;i++) pp[i]=pp[i-1]*p;
  scanf("%s",s+1);
  n=strlen(s+1);
  H.init();
  for (ri i=0;i<N;i++)
    for (ri j=0;j<N;j++) f[i][j]=INF;
  int ans=INF;
  for (ri i=0;i<=n;i++) if (dfs(n,i)<ans) ans=dfs(n,i);
  printf("%d\n",ans);

 

以上是关于SCOI2007压缩的主要内容,如果未能解决你的问题,请参考以下文章

压缩[SCOI2007]

BZOJ 1068[SCOI2007]压缩

SCOI2007压缩

Luogu 2470 [SCOI2007]压缩

BZOJ 1068 SCOI2007 压缩

bzoj1068: [SCOI2007]压缩