zoukankan      html  css  js  c++  java
  • [CF528D] Fuzzy Search

    关于匹配串T在模式串中出现的位置不一定按顺序……只需要保证位置差不过k。

    于是……FFT板题

    #include <bits/stdc++.h>
    #define ll long long 
    using namespace std;
    
    const int N=2e5+10;
    const int inf=0x3f3f3f3f;
    const double Pi=acos(-1);
    
    int ch2int(char c) {
    	if(c=='A') return 1;
    	if(c=='T') return 2;
    	if(c=='G') return 3;
    	if(c=='C') return 4;
    	return 0;
    }
    char str[N];
    int n,m,K,ans,s[N],t[N],SUM[N];
    int p,pL,rev[N<<1];
    
    struct cplx {
    	double x,y;
    	cplx(){} 
    	cplx(double x,double y):x(x),y(y){}
    	cplx operator+(const cplx&d) {return cplx(x+d.x,y+d.y);}
    	cplx operator-(const cplx&d) {return cplx(x-d.x,y-d.y);}
    	cplx operator*(const cplx&d) {return cplx(x*d.x-y*d.y,x*d.y+y*d.x);}
    } a[N<<1],b[N<<1];
    
    void fft(cplx*a,int type) {
    	for(int i=0; i<p; ++i) if(i<rev[i]) swap(a[i],a[rev[i]]);
    	for(int m=1; m<p; m<<=1) {
    		cplx wm(cos(Pi/m),type*sin(Pi/m));
    		for(int i=0; i<p; i+=(m<<1)) {
    			cplx w(1,0),tmp;
    			for(int j=0; j<m; ++j,w=w*wm) {
    				tmp=w*a[m+i+j];
    				a[m+i+j]=a[i+j]-tmp;
    				a[i+j]=a[i+j]+tmp;
    			}
    		}
    	}
    	if(type<0) for(int i=0; i<p; ++i) a[i].x/=p;
    }
    
    void solve(int c) {
    	memset(a,0,sizeof a);
    	memset(b,0,sizeof b);
    	for(int i=0,p=-inf; i<n; ++i) {
    		if(s[i]==c) p=i;
    		if(i-p<=K) a[i].x=1;
    	}
    	for(int i=n-1,p=inf; ~i; --i) {
    		if(s[i]==c) p=i;
    		if(p-i<=K) a[i].x=1;
    	}
    	for(int i=0; i<m; ++i) if(t[i]==c) b[m-i-1].x=1;
    	fft(a,1);  fft(b,1);
    	for(int i=0; i<p; ++i) a[i]=a[i]*b[i];
    	fft(a,-1);
    	for(int i=0; i<n; ++i) SUM[i]+=int(a[i].x+0.5);
    }
    
    int main() {
    	scanf("%d%d%d",&n,&m,&K);
    	scanf("%s",str); for(int i=0; i<n; ++i) s[i]=ch2int(str[i]);
    	scanf("%s",str); for(int i=0; i<n; ++i) t[i]=ch2int(str[i]);
    	for(p=1,pL=0; p<(n+m-1); p<<=1,pL++);
    	for(int i=0; i<p; ++i) rev[i]=(rev[i>>1]>>1)|((i&1)<<(pL-1));
    	for(int i=1; i<=4; ++i) solve(i);
    	for(int i=0; i<n; ++i) ans+=(SUM[i]>=m);
    	printf("%d
    ",ans);
    	return 0;
    }
    
  • 相关阅读:
    Android开发与Sequoyah的安装问题
    Discuz 数据库各表的作用
    jQuery-File-Upload $(...).fileupload is not a function $.widget is not a function
    phpstorm xdebug 无法断点调试问题
    Android Service 启动流程
    Discuz! 全局变量说明
    Discuz! X3 数据表、数据字段说明
    Spring Boot 搭建
    Android组件化开发(注意事项)
    NestedScrollView嵌套RecycleView发生的小问题
  • 原文地址:https://www.cnblogs.com/nosta/p/11026640.html
Copyright © 2011-2022 走看看