枚举听牌 再枚举对子、刻子、顺子。
记录下每一种牌的数量,e数组代表当前的情况,对数量大于3的种类的牌来说,%3就意味着拿出刻子,取模后剩下不够3的只能和顺子凑,所以它后面的两张牌要减去前面的数量。注意j要枚举到n+2,这样可以避免越界。
#include<cstdio>
#include<iostream>
#include<algorithm>
#include<cstring>
using namespace std;
int n,m;
bool flag;
int cnt[510],e[510];
bool check()
{
for(int i=1;i<=n;i++)
{
if(cnt[i]>=2)
{
bool q=true;
cnt[i]-=2;
for(int j=1;j<=n+2;j++)
{
e[j]=cnt[j];
}
for(int j=1;j<=n+2;j++)
{
if(e[j]<0)
{
q=false;
break;
}
e[j]%=3;
e[j+1]-=e[j];
e[j+2]-=e[j];
}
cnt[i]+=2;
if(q==true) return true;
}
}
return false;
}
int main()
{
scanf("%d%d",&n,&m);
for(int i=1;i<=3*m+1;i++)
{
int x;
scanf("%d",&x);
cnt[x]++;
}
for(int i=1;i<=n;i++)
{
cnt[i]++;
memset(e,0,sizeof(e));
if(check()==true)
{
flag=true;
printf("%d ",i);
}
cnt[i]--;
}
if(flag==false) printf("NO");
return 0;
}