题意翻译
桌上有4堆糖果,每堆有N(N≤40)颗。佳佳有一个最多可以装5颗糖的小篮子。他每次 选择一堆糖果,把最顶上的一颗拿到篮子里。如果篮子里有两颗颜色相同的糖果,佳佳就把 它们从篮子里拿出来放到自己的口袋里。如果篮子满了而里面又没有相同颜色的糖果,游戏 结束,口袋里的糖果就归他了。当然,如果佳佳足够聪明,他有可能把堆里的所有糖果都拿 走。为了拿到尽量多的糖果,佳佳该怎么做呢?
来自:刘汝佳《算法竞赛入门经典》
题目描述
输入输出格式
输入格式:输入输出样例
#1:
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstdlib>
#include<cmath>
#include<cstring>
#define maxn 41
using namespace std;
int candy[5],n,l[5],dp[maxn][maxn][maxn][maxn],f[5][maxn],num;
int dfs(int Q,int num)
{
int a,b,c,d;
if(l[1]==n||l[2]==n||l[3]==n||l[4]==n||num==5)
if(dp[l[1]][l[2]][l[3]][l[4]])
return dp[l[1]][l[2]][l[3]][l[4]];
for(int i=1;i<=4;i++)
{
if(l[i]<n)
{
int j=1<<f[i][l[i]];
l[i]++;
if(Q&j)dp[l[1]][l[2]][l[3]][l[4]]=max(dp[l[1]][l[2]][l[3]][l[4]],dfs(Q-j,num-1)+1);
else dp[l[1]][l[2]][l[3]][l[4]]=max(dp[l[1]][l[2]][l[3]][l[4]],dfs(Q+j,num+1));
l[i]--;
}
}
return dp[l[1]][l[2]][l[3]][l[4]];
}
int main()
{
while(cin>>n&&n!=0)
{
memset(dp,0,sizeof dp);
memset(l,0,sizeof l);
for(int i=0;i<n;i++)
for(int j=0;j<n;j++)
cin>>f[j][i];
cout<<dfs(0,0)<<endl;
}
}
#2:
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstdlib>
#include<cmath>
#include<cstring>
#define maxn 41
using namespace std;
int candy[5],n,l[5],dp[maxn][maxn][maxn][maxn],f[5][maxn],num;
int dfs(int Q,int num)
{
int a,b,c,d;
if(l[1]==n||l[2]==n||l[3]==n||l[4]==n||num==5) return 0;
if(dp[l[1]][l[2]][l[3]][l[4]])
return dp[l[1]][l[2]][l[3]][l[4]];
for(int i=1;i<=4;i++)
{
if(l[i]<n)
{
int j=1<<f[i][l[i]];
l[i]++;
if(Q&j)dp[l[1]][l[2]][l[3]][l[4]]=max(dp[l[1]][l[2]][l[3]][l[4]],dfs(Q-j,num-1)+1);
else dp[l[1]][l[2]][l[3]][l[4]]=max(dp[l[1]][l[2]][l[3]][l[4]],dfs(Q+j,num+1));
l[i]--;
}
}
return dp[l[1]][l[2]][l[3]][l[4]];
}
int main()
{
while(cin>>n)
{
if(n==0)break;
memset(dp,0,sizeof dp);
memset(l,0,sizeof l);
for(int i=0;i<4;i++)
for(int j=0;j<n;j++)
cin>>f[i][j];
cout<<dfs(0,0)<<endl;
}
}
#3:
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstdlib>
#include<cmath>
#include<cstring>
#define maxn 41
using namespace std;
int n,l[5],dp[maxn][maxn][maxn][maxn],f[5][maxn];
int dfs(int Q,int num)
{
if(l[1]==n&&l[2]==n&&l[3]==n&&l[4]==n&&num==5) return dp[l[1]][l[2]][l[3]][l[4]]=0;
if(dp[l[1]][l[2]][l[3]][l[4]])
return dp[l[1]][l[2]][l[3]][l[4]];
for(int i=0;i<4;i++)
{
if(l[i]<n)
{
int j=1<<f[i][l[i]];
l[i]++;
if(Q&j)dp[l[1]][l[2]][l[3]][l[4]]=max(dp[l[1]][l[2]][l[3]][l[4]],dfs(Q-j,num-1)+1);
else if(num<5)dp[l[1]][l[2]][l[3]][l[4]]=max(dp[l[1]][l[2]][l[3]][l[4]],dfs(Q+j,num+1));
l[i]--;
}
}
return dp[l[1]][l[2]][l[3]][l[4]];
}
int main()
{
while(cin>>n)
{
if(n==0)break;
memset(dp,0,sizeof dp);
memset(l,0,sizeof l);
for(int i=0;i<4;i++)
for(int j=0;j<n;j++)
cin>>f[i][j];
cout<<dfs(0,0)<<endl;
}
}
#4:
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstdlib>
#include<cmath>
#include<cstring>
#define maxn 41
using namespace std;
int n,l[5],dp[maxn][maxn][maxn][maxn],f[maxn][5];
int dfs(int Q,int num)
{
if(dp[l[0]][l[1]][l[2]][l[3]]!=-1)
return dp[l[0]][l[1]][l[2]][l[3]];
if((l[0]==n&&l[1]==n&&l[2]==n&&l[3]==n)||num==5) return dp[l[0]][l[1]][l[2]][l[3]]=0;
for(int i=0;i<4;i++)
{
if(l[i]<n)
{
int j=1<<f[l[i]][i];
l[i]++;
if(j&Q)dp[l[0]][l[1]][l[2]][l[3]]=max(dp[l[0]][l[1]][l[2]][l[3]],dfs(Q-j,num-1)+1);
else if(num<5)dp[l[0]][l[1]][l[2]][l[3]]=max(dp[l[0]][l[1]][l[2]][l[3]],dfs(Q+j,num+1));
l[i]--;
}
}
return dp[l[0]][l[1]][l[2]][l[3]];
}
int main()
{
while(cin>>n)
{
if(n==0)break;
memset(dp,-1,sizeof dp);
memset(l,0,sizeof l);
for(int i=0;i<n;i++)
for(int j=0;j<4;j++)
cin>>f[i][j];
cout<<dfs(0,0)<<endl;
}
}
#5:
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstdlib>
#include<cmath>
#include<cstring>
#define maxn 41
using namespace std;
int n,l[5],dp[maxn][maxn][maxn][maxn],f[maxn][5];
int dfs(int Q,int num)
{
if(dp[l[0]][l[1]][l[2]][l[3]]!=-1)
return dp[l[0]][l[1]][l[2]][l[3]];
if((l[0]==n&&l[1]==n&&l[2]==n&&l[3]==n)||num==5) return dp[l[0]][l[1]][l[2]][l[3]]=0;
for(int i=0;i<4;i++)
{
if(l[i]<n)
{
int j=1<<f[l[i]][i];
l[i]++;
if(j&Q)dp[l[0]][l[1]][l[2]][l[3]]=max(dp[l[0]][l[1]][l[2]][l[3]],dfs(Q-j,num-1)+1);
else if(num<5)dp[l[0]][l[1]][l[2]][l[3]]=max(dp[l[0]][l[1]][l[2]][l[3]],dfs(Q+j,num+1));
l[i]--;
}
}
return dp[l[0]][l[1]][l[2]][l[3]];
}
int main()
{
while(cin>>n)
{
if(n==0)break;
memset(dp,-1,sizeof dp);
memset(l,0,sizeof l);
for(int i=0;i<n;i++)
for(int j=0;j<4;j++)
cin>>f[i][j];
cout<<dfs(0,0)<<endl;
}
}
AC代码:
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstdlib>
#include<cmath>
#include<cstring>
#define maxn 41
using namespace std;
int n,l[5],dp[maxn][maxn][maxn][maxn],f[maxn][5];
int dfs(int Q,int num)
{
int &now=dp[l[0]][l[1]][l[2]][l[3]];
if(now!=-1)
return now;
if((l[0]==n&&l[1]==n&&l[2]==n&&l[3]==n)||num==5) return now=0;
for(int i=0;i<4;i++)
{
if(l[i]<n)
{
int j=1<<f[l[i]][i];
l[i]++;
if(j&Q)now=max(now,dfs(Q-j,num-1)+1);
else if(num<5)now=max(now,dfs(Q+j,num+1));
l[i]--;
}
}
return now;
}
int main()
{
while(1)
{
cin>>n;
if(n==0)break;
memset(dp,-1,sizeof dp);
memset(l,0,sizeof l);
for(int i=0;i<n;i++)
for(int j=0;j<4;j++)
cin>>f[i][j];
cout<<dfs(0,0)<<endl;
}
}
很好奇为什么#5和AC代码就是换了个名字答案却不一样。