HDU 5972 Regular Number(ShiftAnd+读入优化)
生活随笔
收集整理的這篇文章主要介紹了
HDU 5972 Regular Number(ShiftAnd+读入优化)
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
?
【題目鏈接】?http://acm.hdu.edu.cn/showproblem.php?pid=5972
?
【題目大意】
給出一個字符串,找出其中所有的符合特定模式的子串位置,符合特定模式是指,該子串的長度為n,并且第i個字符需要在給定的字符集合Si中?
?
【題解】
利用ShiftAnd匹配算法。
bt[i]表示字符i允許在哪些位置上出現,我們將匹配成功的位置保存在dp中,那么就可以用dp[i]=dp[i-1]<<1&bt[s[i]]來更新答案了
利用滾動數組和bitset可以來優化這樣的運算,當一個位置的匹配在更新的過程中沒有丟失,
即始終在特定模式中直到定長,那么這個位置就是成功匹配位,復雜度為O(nm/64)
由于輸入的數據量龐大,因此需要讀入和輸出優化。
終于AC了,補上大連賽區的遺憾。
?
【代碼】
#include <cstdio>
#include <bitset>
#include <cstring>
using namespace std;
const int M=1010,N=5000010,U=256;
bitset<M> dp[2],bt[U];
int n,m,x,id[U],cnt,l;
char s[N];
namespace fastIO{#define BUF_SIZE 100000#define OUT_SIZE 1000000bool IOerror=0;inline char nc(){static char buf[BUF_SIZE],*p1=buf+BUF_SIZE,*pend=buf+BUF_SIZE;if(p1==pend){p1=buf; pend=buf+fread(buf,1,BUF_SIZE,stdin);if (pend==p1){IOerror=1;return -1;}}return *p1++;}inline bool blank(char ch){return ch==' '||ch=='\n'||ch=='\r'||ch=='\t';}inline int read(char *s){char ch=nc();for(;blank(ch);ch=nc());if(IOerror)return 0;for(;!blank(ch)&&!IOerror;ch=nc())*s++=ch;*s=0;return 1;}inline int RI(int &a){char ch=nc(); a=0;for(;blank(ch);ch=nc());if(IOerror)return 0;for(;!blank(ch)&&!IOerror;ch=nc())a=a*10+ch-'0';return 1;}struct Ostream_fwrite{char *buf,*p1,*pend;Ostream_fwrite(){buf=new char[BUF_SIZE];p1=buf;pend=buf+BUF_SIZE;}void out(char ch){if (p1==pend){fwrite(buf,1,BUF_SIZE,stdout);p1=buf;}*p1++=ch;}void flush(){if (p1!=buf){fwrite(buf,1,p1-buf,stdout);p1=buf;}}~Ostream_fwrite(){flush();}}Ostream;inline void print(char x){Ostream.out(x);}inline void println(){Ostream.out('\n');}inline void flush(){Ostream.flush();}char Out[OUT_SIZE],*o=Out;inline void print1(char c){*o++=c;}inline void println1(){*o++='\n';}inline void flush1(){if (o!=Out){if (*(o-1)=='\n')*--o=0;puts(Out);}}struct puts_write{~puts_write(){flush1();}}_puts;
};
void init(){cnt=0;for(int i='0';i<='9';i++)id[i]=cnt++;
}
void ShiftAnd(int n,int m){int cur=1,f=0;dp[0].reset(); dp[0].set(0);for(int i=1;i<=n;i++,cur^=1){dp[cur]=dp[cur^1]<<1&bt[id[s[i]]];dp[cur].set(0);if(dp[cur][m]){for(int j=i-m+1;j<=i;j++)fastIO::print(s[j]);fastIO::println();}}
}
int main(){ //freopen("demo.in","r",stdin);//freopen("demo.out","w",stdout);init();while(fastIO::RI(m)){ for(int i=0;i<cnt;i++)bt[i].reset();for(int i=1;i<=m;i++){fastIO::RI(l);for(int j=1;j<=l;j++){fastIO::RI(x);bt[x].set(i);}}fastIO::read(s+1); n=strlen(s+1);ShiftAnd(n,m);}return 0;
}
轉載于:https://www.cnblogs.com/forever97/p/hdu5972.html
總結
以上是生活随笔為你收集整理的HDU 5972 Regular Number(ShiftAnd+读入优化)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: c# unity PlayerPrefs
- 下一篇: 求没有花香没有树高是什么歌词