• bzoj3790


    观察发现,这道题目其实就相当于一个最小区间覆盖问题
    这里的区间是指以每个点为中心的最长回文串
    很久没写manacher,有点感动
    不得不说manacher是一个非常好的算法

      1 var s:array[0..100010] of char;
      2     c,l,r,f,p:array[0..100010] of longint;
      3     i,j,t,n,m,ans,k,right:longint;
      4     ch:char;
      5 
      6 procedure swap(var a,b:longint);
      7   var c:longint;
      8   begin
      9     c:=a;
     10     a:=b;
     11     b:=c;
     12   end;
     13 
     14 function min(a,b:longint):longint;
     15   begin
     16     if a>b then exit(b) else exit(a);
     17   end;
     18 
     19 function lowbit(x:longint):longint;
     20   begin
     21     exit(x and (-x));
     22   end;
     23 
     24 procedure sort(ll,rr: longint);
     25   var i,j,x,y: longint;
     26   begin
     27     i:=ll;
     28     j:=rr;
     29     x:=r[(ll+rr) shr 1];
     30     y:=l[(ll+rr) shr 1];
     31     repeat
     32       while (r[i]<x) or (r[i]=x) and (l[i]<y) do inc(i);
     33       while (x<r[j]) or (r[j]=x) and (y<l[j]) do dec(j);
     34       if not(i>j) then
     35       begin
     36         swap(r[i],r[j]);
     37         swap(l[i],l[j]);
     38         inc(i);
     39         j:=j-1;
     40       end;
     41     until i>j;
     42     if ll<j then sort(ll,j);
     43     if i<rr then sort(i,rr);
     44   end;
     45 
     46 function ask(x:longint):longint;
     47   begin
     48     if x=0 then exit(0);
     49     ask:=n+1;
     50     while x<=n do  //因为求的是后缀最小值,事实上只要将查询和修改的范围换一下即可
     51     begin
     52       ask:=min(ask,c[x]);
     53       x:=x+lowbit(x);
     54     end;
     55   end;
     56 
     57 procedure add(i:longint);
     58   var x:longint;
     59   begin
     60     x:=r[i];
     61     while x>0 do
     62     begin
     63       c[x]:=min(c[x],f[i]);
     64       x:=x-lowbit(x);
     65     end;
     66   end;
     67 
     68 begin
     69   while true do
     70   begin
     71     read(ch);
     72     if not((ch>='a') and (ch<='z')) then break;
     73     s[0]:='$';
     74     s[1]:='#';
     75     m:=1;
     76     n:=0;
     77     while (ch>='a') and (ch<='z') do
     78     begin
     79       inc(n);
     80       inc(m);
     81       s[m]:=ch;
     82       inc(m);
     83       s[m]:='#'; //将回文串的奇偶转化为一种情况
     84       read(ch);
     85     end;
     86     s[m+1]:=' ';
     87     readln;
     88     k:=0;
     89     right:=0;
     90     t:=0;
     91     fillchar(p,sizeof(p),0);
     92     for i:=1 to m do
     93     begin
     94       if right>i then   //manacher的核心
     95         p[i]:=min(p[2*k-i],right-i)
     96       else p[i]:=1;
     97       while s[i+p[i]]=s[i-p[i]] do inc(p[i]);
     98       if p[i]+i>right then
     99       begin
    100         right:=p[i]+i;
    101         k:=i;
    102       end;
    103       if (s[i]='#') and (p[i]=1) then continue
    104       else begin
    105         inc(t);
    106         l[t]:=(i-p[i]+2) div 2;
    107         r[t]:=(i+p[i]-2) div 2;
    108       end;
    109     end;
    110     sort(1,t);  //解决区间覆盖问题,右端点排序
    111     ans:=n;
    112     for i:=1 to n do
    113       c[i]:=n+1;
    114     for i:=1 to t do
    115     begin
    116       f[i]:=ask(l[i]-1)+1; //以前这个问题我都是用单调队列的,这里写了树状数组,更简明
    117       if r[i]=n then ans:=min(ans,f[i]);
    118       add(i);
    119     end;
    120     writeln(ans-1);
    121   end;
    122 end.
    View Code
  • 相关阅读:
    APICloud联合腾讯云推出“云主机解决方案“,各种福利等你拿
    WiFi模块Demo(新手教程)图文详解模块使用教程
    移动APP 微信支付完整过程(wxPay 方案一)
    APICloud开发者进阶之路 | txLive模块(直播类)试用分享
    解决R语言临时文件目录的问题(tempdir、tempfile)
    CentOS下SparkR安装部署:hadoop2.7.3+spark2.0.0+scale2.11.8+hive2.1.0
    Extending sparklyr to Compute Cost for K-means on YARN Cluster with Spark ML Library
    Running R jobs quickly on many machines(转)
    R语言快速深度学习进行回归预测(转)
    sparklyr包:实现Spark与R的接口
  • 原文地址:https://www.cnblogs.com/phile/p/4473042.html
Copyright © 2020-2023  润新知