【BubbleCup X】G:Bathroom terminal

一个hash的题

对?出现位置直接暴力枚举,然后hash判断下,扔进map里

cf的评测机跑的针tm块

#include<bits/stdc++.h>
const int N=100010;
const int bas=31;
typedef long long ll;
typedef unsigned long long ull;
using namespace std;
int n,m,cnt,len,ans;
char s[N],ss[N];
map<ull,int>mps[N];
map<pair<int,ull>,int>mps2;
int hs[N],a[N];
inline int read(){
    int f=1,x=0;char ch;
    do{ch=getchar();if(ch=='-')f=-1;}while(ch<'0'||ch>'9');
    do{x=x*10+ch-'0';ch=getchar();}while(ch>='0'&&ch<='9');
    return f*x;
}
inline void check(){
    for(int i=1;i<=cnt;i++)if(a[i]==-1)s[hs[i]]='?';else s[hs[i]]='a'+a[i];
    ull h=0;int tmp=0;
    for(int i=1;i<=len;i++)if(s[i]!='?')++tmp,h=h*bas+s[i]-'a';
    if(!mps2.count(make_pair(tmp,h))){ans+=mps[tmp][h];mps2[make_pair(tmp,h)]=1;}
}
inline void dfs(int now){
    if(now==cnt+1){check();return;}
    for(int i=-1;i<=4;i++)a[now]=i,dfs(now+1);
}
int main(){
    n=read();m=read();
    for(int i=1;i<=n;i++){
        scanf("%s",s+1);len=strlen(s+1);
        ull h=0;for(int j=1;j<=len;j++)h=h*bas+s[j]-'a';
        mps[len][h]++;
    }
    while(m--){
        scanf("%s",s+1);len=strlen(s+1);cnt=0;
        for(int j=1;j<=len;j++)if(s[j]=='?')hs[++cnt]=j;ans=0;
        mps2.clear();dfs(1);
        printf("%d\n",ans);
    }
}

 

posted @ 2017-09-04 19:52  zcysky  阅读(453)  评论(0编辑  收藏  举报