http://acm.hdu.edu.cn/showproblem.php?pid=5745
第一次使用bitset这个东西,优点是可以常数优化,而此题优雅的bitset转移刚好可以卡过
转移方程是看的这篇博客,
http://blog.csdn.net/u012015746/article/details/51992281
“
首先得出一个
dp
式子,
dp[i][j][k]
表示
A
匹配到
i
,
B
匹配到
j
而
k
表示
Bj
的交换情况,
0
为不动,
1
与前面交换,
2
与后面交换
转移方程为:
dpi,j,0=dpi−1,j−1,0
or
dpi−1,j−1,1
,
(Ai==Bj)
dpi,j,1=dpi−1,j−1,2
,
(Ai==Bj−1)
dpi,j,2=dpi−1,j−1,0
or
dpi−1,j−1,1
,
(Ai==Bj+1)
“
此题数据改过,虽然博主的代码现在提交是t的,但转移方程很好理解
在转移的时候稍微改改减少几次位运算次数就可以了
#include<bits/stdc++.h>
#define eps 1e-9
#define PI 3.141592653589793
#define bs 1000000007
#define bsize 256
#define MEM(a) memset(a,0,sizeof(a))
typedef long long ll;
using namespace std;
char s[100005],p[5005];
char ans[100005];
int n,m;
bitset<100005>dp[2][3];
bitset<100005>v[26];
int main()
{
int T,i,j;
// while(cin>>T)
cin>>T;
{
while(T--)
{
cin>>n>>m;
scanf(" %s",s);
scanf(" %s",p);
for(i=0;i<26;i++)
v[i].reset();
for(i=0;i<n;i++)
{
v[s[i]-'a'].set(n-i-1);
}
int now=1,pre=0;
dp[0][0]=v[p[0]-'a'];
dp[0][1].reset();
if(m!=1)
dp[0][2]=v[p[1]-'a'];
for(i=1;i<m;i++)
{
int i1=p[i]-'a';
int i2=p[i-1]-'a';
int i3=p[i+1]-'a';
dp[now][0]=((dp[pre][0]|dp[pre][1])>>1)&v[i1];
dp[now][1]=(dp[pre][2]>>1)&v[i2];
if(i!=m-1)
dp[now][2]=((dp[pre][0]|dp[pre][1])>>1)&v[i3];
swap(now,pre);
}
for(i=0;i<n;i++)
{
if(n-i-m>=0&&(dp[pre][0][n-i-m]|dp[pre][1][n-i-m]))
ans[i]='1';
else
ans[i]='0';
}
ans[n]=0;
printf("%s\n",ans);
}
}
return 0;
}