标签:
题意 :
给你 N 种 长方体, 每种无限多
长方体可以堆叠,不过接触的尺寸 长宽必须严格小于下方的长方体
问最多长方体可以堆多高
思路:
动态规划
先把每种 长方体可能的形态存下来
然后求最大递减子序列和
#include<iostream> #include<cstdio> #include<algorithm> #include<cstring> using namespace std; typedef long long ll; const int maxn = 1900; struct Node { ll x, y, z; }Num[maxn]; int Dp[maxn]; bool cmp(Node a,Node b) { if(a.x > b.x) return true; if(a.x == b.x && a.y > b.y) return true; return false; } int main() { int n, Kase = 1; while(scanf("%d",&n) && n) { int a, b, c,cnt = 0; for(int i = 0; i < n; ++i) { scanf("%d%d%d",&a,&b,&c);// 这个地方多WA了几发,要注意长方体形态 if(a > b) swap(a,b); if(b > c) swap(b,c); if(a > b) swap(a,b); Num[cnt].x = c, Num[cnt].y = b, Num[cnt++].z = a; Num[cnt].x = c, Num[cnt].y = a, Num[cnt++].z = b; Num[cnt].x = b, Num[cnt].y = a, Num[cnt++].z = c; } n = n * 3; sort(Num,Num+cnt,cmp); for(int i = 0; i < cnt; ++i) Dp[i] = Num[i].z; //int Sum = 0; for(int i = cnt-2; i >= 0; --i) { for(int j = i + 1 ; j < cnt; ++j) if(Num[j].x < Num[i].x && Num[j].y < Num[i].y) { if(Dp[i] < Dp[j] + Num[i].z) Dp[i] = Dp[j] + Num[i].z; } } int Sum = Dp[0]; for(int i = 0; i < cnt; ++i) if(Dp[i] > Sum) Sum = Dp[i]; printf("Case %d: maximum height = %d\n",Kase++,Sum); } }
标签:
原文地址:http://www.cnblogs.com/aoxuets/p/4735063.html