题意:给定一个w*h的蛋糕,将其分成m份,也就是切m-1刀(必须保证每次都将一块蛋糕切成两份,按照水平或者竖直),求最后m份中最大的那份的面积最小是多少。
题解:记忆化搜索,dp[k][i][j]为将一块i*j的蛋糕切k刀的最大面积的最小值,枚举下一刀的横竖以及切的位置和其中一份的刀数。
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
const int inf=0x3f3f3f3f;
int dp[405][25][25];
int dfs(int m,int w,int h)
{
if(dp[m][w][h]!=inf)
return dp[m][w][h];
else if(m==0)
return dp[m][w][h]=w*h;
else
{
int ans=inf;
for(int i=1,lim=w/2+1;i<=lim;i++)
for(int k=0;k<=m-1;k++)
ans=min(ans,max(dfs(k,i,h),dfs(m-1-k,w-i,h)));
for(int i=1,lim=h/2+1;i<=lim;i++)
for(int k=0;k<=m-1;k++)
ans=min(ans,max(dfs(k,w,i),dfs(m-1-k,w,h-i)));
return dp[m][w][h]=ans;
}
}
int main()
{
int w,h,m;
memset(dp,0x3f,sizeof(dp));
while(scanf("%d%d%d",&w,&h,&m),w||h||m)
printf("%d\n",dfs(m-1,w,h));
return 0;
}