zoukankan      html  css  js  c++  java
  • bzoj 3214: [Zjoi2013]丽洁体

    Description

    平时的练习和考试中,我们经常会碰上这样的题:命题人给出一个例句,要我们类比着写句子。这种往往被称为仿
    写的题,不单单出现在小学生的考试中,也有时会出现在中考中。许多同学都喜欢做这种题,因为较其它题显得有
    趣。仿写的句子往往具有“A__B__C”的形式,其中A,B,C是给定的由一个或多个单词组成的短句,空的部分需要
    学生填写。当然,考试的时候空在那里也是可以的。例如,“其实天不暗阴云终要散,其实 ,其实 ,其实路不远
    一切会如愿,艰难困苦的日子里我为你祈祷,请你保重每一天”。再比如,“见了大海的汹涌,没见过大山的巍峨
    ,真是遗憾;见了大山的巍峨,没见过 ,还是遗憾。出发吧,永远出发。 ,人有不老的心情。”由于现在是网络
    时代,我们不再只能仿写命题人命的题,我们可以仿写网上各种句子和段落。2011年3月26日,某人在博客上发布
    了的消息就惹来了很多人的仿写。
    很难过吧。。。考得完爆了。。。
    。。。。。。其实也没什么可以说的。。。都是蒟蒻的借口罢了。。。
    。。。自己果然还只是半吊子水平呢。。。。
    。。。祝大家都能进省队。。。其实只要不要有遗憾就好了呢。。。
    虽然我很遗憾或许不能走下去了。。。。。
    886
    在网络上广泛流传的仿写,因为在某些地方有独到之处,大都被命名为“某某体”。打开人人,刷新微博,你也能
    发现这样和那样的体,比如,对不起体,**说明他爱你体等等。金先生注意到了这一现象,他敏锐地认为这是一个
    很有价值的研究课题,于是就其展开研究,打算发一篇paper。由于在网上发消息,人们有了更大的灵活度,人们
    有时因为表达的需要,还往原本固定的A, B, C中添加一些修饰的词语。这就给辨别一个句子或段落是否是另一个
    句子或段落的仿写增加了困难。金先生现在研究一种形如“ABC”的体作品,其中A, B, C分别是某个由若干单词
    组成的短句,*代表0个或多个单词。他在网上找了大量的体作品,不过很多体作品不太合乎原作者的格式,也就是
    相当于在正规的体作品中插入了0个或多个单词。由于数据量太大,金先生无法一个一个看过去,于是想请你帮忙
    ,去掉尽量少的单词,使它成为指定的体。

    Solution

    首先对于A,C串可以直接贪心求出来,左右两边单调指针分别扫一下即可
    对于B串,也就是要找到一个子序列使得B是它的子串,并最小化这个子序列
    那么贪心即可
    假设匹配的B的第 (i) 位,我们当然希望 (i-1) 位尽量近,所以维护这个东西即可
    (f[i])表示第(i)位的字符最晚在 (T) 串的哪个位置出现
    (g[i])表示匹配前 (i) 位最少删除的字符
    因为每个单词出现次数比较少,所以可以直接遍历 (B) 串的这个单词,把B的每一个单词出现的位置挂链即可
    注意读入很坑的.....

    #include<bits/stdc++.h>
    using namespace std;
    const int N=250010,M=15000000;
    char S[M];int s[N],a[N],b[N],c[N],f[N],g[N];
    vector<int>e[M];
    void init(int *p){
    	char ch=getchar();int len=0;
    	while(ch!='
    ')S[++len]=ch,ch=getchar();
    	for(int i=1,j;i<=len;i=j+1){
    		int t=0;j=i;
    		while(S[j]>='a' && S[j]<='z')t=t*27+S[j]-'a'+1,j++;
    		p[++p[0]]=t;
    	}
    }
    int main(){
      freopen("pp.in","r",stdin);
      freopen("pp.out","w",stdout);
      init(s);init(a);init(b);init(c);
      int l=1,r=s[0],x=1,sum=0,ans=2e8;
      while(x<=a[0]){
    	  while(l<=s[0] && a[x]!=s[l])l++,sum++;
    	  x++;l++;
      }
      x=c[0];
      while(x>=1){
    	  while(r>=1 && c[x]!=s[r])r--,sum++;
    	  x--;r--;
      }
      memset(g,127/3,sizeof(g));
      for(int i=1;i<=b[0];i++)e[b[i]].push_back(i);
      for(int i=l;i<=r;i++){
    	  for(int j=e[s[i]].size()-1;j>=0;j--){
    		  x=e[s[i]][j];
    		  if(x==1)f[x]=i,g[x]=0;
    		  else if(f[x-1])f[x]=i,g[x]=g[x-1]+i-f[x-1]-1;
    		  ans=min(ans,g[b[0]]);
    	  }
      }
      cout<<sum+ans<<endl;
      return 0;
    }
    
    
  • 相关阅读:
    开发板S3C2440挂起NFS步骤
    wind10系统 Atheros AR9271 Wireless Network Adapter USBwifi无线网卡的驱动安装解决无法搜索wifi信号,连接wifi信号无法上网的问题
    编写一个多线程函数实现对数组排序,要求: 1.至少用两个线程 2.数组的元素值可以事先定义好,或者可以从键盘输入(增加一个线程)。 3.用一个线程对数组排序,用另一个线程输出排序结果。 4.保证先排好序,再输出。
    led.c驱动框架2nd
    led.c驱动框架
    文件I/O的操作实例
    Python os.removedirs() 和shutil.rmtree() 用于删除文件夹
    Python os.remove() 删除文件
    Python os.chdir() 方法
    Python os.access() 方法
  • 原文地址:https://www.cnblogs.com/Yuzao/p/8458356.html
Copyright © 2011-2022 走看看