判断和牌.
设(f[i][j][k][0/1])表示选到第(i)种牌,第(i-1)种选(j)张,第(i)种选(k)张,有没有将时的和牌情况.(f[0][0][0][0]=1;)
然后直接转移即可,可以用填表法.
详见代码.
#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#define debug(...) fprintf(stderr,__VA_ARGS__)
#define Debug(x) cout<<#x<<"="<<x<<endl
using namespace std;
typedef long long LL;
const int INF=1e9+7;
inline LL read(){
register LL x=0,f=1;register char c=getchar();
while(c<48||c>57){if(c=='-')f=-1;c=getchar();}
while(c>=48&&c<=57)x=(x<<3)+(x<<1)+(c&15),c=getchar();
return f*x;
}
bool f[105][105][105][2];
int a[105];
int main(){
for(int i=read();i;i--){
for(int i=1;i<=100;i++) a[i]=read();
memset(f,0,sizeof f);
f[0][0][0][0]=1;
for(int i=1;i<=100;i++)
for(int j=0;j<=a[i-1];j++)
for(int k=0;k<=a[i];k++){
if(k>=2) f[i][j][k][1]|=f[i][j][k-2][0];
if(k>=3) f[i][j][k][0]|=f[i][j][k-3][0],f[i][j][k][1]|=f[i][j][k-3][1];
if(k>=4) f[i][j][k][0]|=f[i][j][k-4][0],f[i][j][k][1]|=f[i][j][k-4][1];
if(j>=k&&a[i-2]>=k) f[i][j][k][0]|=f[i-1][a[i-2]-k][j-k][0],f[i][j][k][1]|=f[i-1][a[i-2]-k][j-k][1];
}
puts(f[100][a[99]][a[100]][1]?"Yes":"No");
}
}