http://acm.hdu.edu.cn/showproblem.php?pid=1069

题意:n种木块问最多可以摆多高,每种有无数个,上面木块的长宽必须分别小于下面木块的长宽

注意到每种无数个这个条件是虚的,其实只有三种。dp[i]表示以第 i 块为底可以摆放的最大高度

#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cstring> 

using namespace std; 

struct node{
    int x, y, z; 
}b[105]; 

int cmp(node aa, node bb){
    if(aa.x == bb.x) return aa.y > bb.y; 
    return aa.x > bb.x;  
}

int dp[105]; //以i为底可以放的最大值 

int main(){
    int n;
    int cas = 1;
    while(~scanf("%d", &n), n){
        int st = 0;
        for(int i = 0; i < n; i++){
            int aa, bb, cc;
            scanf("%d %d %d", &aa, &bb, &cc);
            b[st].x = max(aa, bb); b[st].y = min(aa, bb); b[st++].z = cc; 
            b[st].x = max(aa, cc); b[st].y = min(aa, cc); b[st++].z = bb; 
            b[st].x = max(cc, bb); b[st].y = min(cc, bb); b[st++].z = aa; 
        }
        sort(b, b+st, cmp);
        memset(dp, 0, sizeof(dp));
        for(int i = 0; i < st; i++){
            dp[i] = b[i].z; 
            for(int j = i - 1; j >= 0; j--){
                if(b[j].x > b[i].x && b[j].y > b[i].y)
                    dp[i] = max(dp[i], dp[j] + b[i].z);
            }
        }
        int ans = 0;
        for(int i = 0; i < st; i++)
            ans = max(ans, dp[i]);
        printf("Case %d: maximum height = %d\n", cas++, ans); 
    }
    return 0;
}
View Code