UVa 12099 The Bookcase (DP)
题意:有 n 本书,每本书有一个高度和宽度,然后让你制作一个3层的书架,可以放下所有的书,并且要高*宽尽量小。
析:先把所有的书按高度进行排序,然后dp[i][j][k] 表示 前 i 本书,第二 层的宽度是 j,第三层的宽度是 k,第二层和第三层的高度最小,首先我们可以先最高的那本书放到第一层,那么这一层的高度就确定了,同理,在放第二层和第三层的时候,如果是第一本书,那么这一层的高度就已经确定了,为什么不表示第一层的宽度呢,因为总宽度是确定的,如果第二层的宽度和第三层的宽度知道了,那么第一层也就确定了。有了这些就可以进行状态转移了。注意不要转移无用的状态以降低时间复杂度。
有三种决策,1 放在第一层,dp[i+1][j][k] = min{ dp[i][j][k] }
2.放在第二层,那么又有两种情况,第一次放,还是不是第一次放
if(j == 0) dp[i+1][j+w][k] = min{ dp[i][j][k] + h }
else dp[i+1][j+w][k] = min{ dp[i][j][k] }
3.放在第三层,这一种和第二层一样。
代码如下:
#pragma comment(linker, "/STACK:1024000000,1024000000")
#include <cstdio>
#include <string>
#include <cstdlib>
#include <cmath>
#include <iostream>
#include <cstring>
#include <set>
#include <queue>
#include <algorithm>
#include <vector>
#include <map>
#include <cctype>
#include <cmath>
#include <stack>
#include <sstream>
#include <list>
#include <assert.h>
#include <bitset>
#define debug() puts("++++");
#define gcd(a, b) __gcd(a, b)
#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1
#define fi first
#define se second
#define pb push_back
#define sqr(x) ((x)*(x))
#define ms(a,b) memset(a, b, sizeof a)
#define sz size()
#define pu push_up
#define pd push_down
#define cl clear()
#define all 1,n,1
#define FOR(x,n) for(int i = (x); i < (n); ++i)
#define freopenr freopen("in.txt", "r", stdin)
#define freopenw freopen("out.txt", "w", stdout)
using namespace std; typedef long long LL;
typedef unsigned long long ULL;
typedef pair<int, int> P;
const int INF = 0x3f3f3f3f;
const double inf = 1e20;
const double PI = acos(-1.0);
const double eps = 1e-8;
const int maxn = 200000 + 10;
const LL mod = 1e9 + 7;
const int dr[] = {-1, 0, 1, 0};
const int dc[] = {0, 1, 0, -1};
const char *de[] = {"0000", "0001", "0010", "0011", "0100", "0101", "0110", "0111", "1000", "1001", "1010", "1011", "1100", "1101", "1110", "1111"};
int n, m;
const int mon[] = {0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
const int monn[] = {0, 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
inline bool is_in(int r, int c) {
return r > 0 && r <= n && c > 0 && c <= m;
} int dp[2][2105][2105];
struct Node{
int h, w;
bool operator < (const Node &p) const {
return h > p.h;
}
};
Node a[80];
int sum[maxn]; int main(){
int T; cin >> T;
while(T--){
scanf("%d", &n);
for(int i = 1; i <= n; ++i) scanf("%d %d", &a[i].h, &a[i].w);
sort(a + 1, a + n + 1);
for(int i = 2; i <= n; ++i) sum[i] = sum[i-1] + a[i].w;
int cnt = 0;
ms(dp[0], INF);
dp[0][0][0] = 0;
for(int i = 1; i < n; ++i, cnt ^= 1){
ms(dp[cnt^1], INF);
for(int j = 0; j <= sum[i]; ++j){
for(int k = 0; k <= sum[i]; ++k){
if(j + k > sum[i]) break;
if(dp[cnt][j][k] == INF) continue;
dp[cnt^1][j][k] = min(dp[cnt^1][j][k], dp[cnt][j][k]);
if(j == 0) dp[cnt^1][a[i+1].w][k] = min(dp[cnt^1][a[i+1].w][k], dp[cnt][j][k] + a[i+1].h);
else dp[cnt^1][j+a[i+1].w][k] = min(dp[cnt^1][j+a[i+1].w][k], dp[cnt][j][k]);
if(k == 0) dp[cnt^1][j][a[i+1].w] = min(dp[cnt^1][j][a[i+1].w], dp[cnt][j][k] + a[i+1].h);
else dp[cnt^1][j][k+a[i+1].w] = min(dp[cnt^1][j][k+a[i+1].w], dp[cnt][j][k]);
}
}
} int ans = INF;
for(int i = 0; i <= sum[n]; ++i)
for(int j = 0; j <= sum[n]; ++j){
if(i + j > sum[n]) break;
if(dp[cnt][i][j] == INF) continue;
if(i == 0 || j == 0) continue;
ans = min(ans, (dp[cnt][i][j] + a[1].h) * max(j, max(i, sum[n]-j-i+a[1].w)));
}
printf("%d\n", ans);
}
return 0;
}
UVa 12099 The Bookcase (DP)的更多相关文章
- UVa 12099 The Bookcase - 动态规划
题目大意 给定一些书,每个书有一个高度和宽度,然后将它们放到一个三层的书架里(要求每一层都不为空).定义书架的大小为每层最大的高度和 乘 每层宽度和的最大值.求最小的书架大小. 显然动态规划(直觉,没 ...
- UVA - 12099 The Bookcase
No wonder the old bookcase caved under the massive piles of books Tom had stacked on it. He had bett ...
- 【暑假】[深入动态规划]UVa 10618 The Bookcase
UVa 12099 The Bookcase 题目: http://acm.hust.edu.cn/vjudge/problem/viewProblem.action?id=42067 思路: ...
- UVA.674 Coin Change (DP 完全背包)
UVA.674 Coin Change (DP) 题意分析 有5种硬币, 面值分别为1.5.10.25.50,现在给出金额,问可以用多少种方式组成该面值. 每种硬币的数量是无限的.典型完全背包. 状态 ...
- uva 10817(数位dp)
uva 10817(数位dp) 某校有m个教师和n个求职者,需讲授s个课程(1<=s<=8, 1<=m<=20, 1<=n<=100).已知每人的工资c(10000 ...
- UVA 11404 Palindromic Subsequence[DP LCS 打印]
UVA - 11404 Palindromic Subsequence 题意:一个字符串,删去0个或多个字符,输出字典序最小且最长的回文字符串 不要求路径区间DP都可以做 然而要字典序最小 倒过来求L ...
- uva 10453 - Make Palindrome(dp)
题目链接:10453 - Make Palindrome 题目大意:给出一个字符串,通过插入字符使得原字符串变成一个回文串,要求插入的字符个数最小,并且输出最后生成的回文串. 解题思路:和uva 10 ...
- uva 10671 - Grid Speed(dp)
题目链接:uva 10671 - Grid Speed 题目大意:给出N,表示在一个N*N的网格中,每段路长L,如今给出h,v的限制速度,以及起始位置sx,sy,终止位置ex,ey,时间范围st,et ...
- uva 1331 - Minimax Triangulation(dp)
option=com_onlinejudge&Itemid=8&page=show_problem&category=514&problem=4077&mosm ...
随机推荐
- 安装Elastix-2.4版本
首先,下载Elastix地址:http://www.elastix.org,下载里面的2.4版本 第一步:选择安装,Enter 选择语言,默认就行 选择us,默认 选择全部 选择默认分区,点击OK 配 ...
- 11_java之接口和多态
01接口的概念 * A:接口的概念 接口是功能的集合,同样可看做是一种数据类型,是比抽象类更为抽象的”类”. 接口只描述所应该具备的方法,并没有具体实现,具体的实现由接口的实现类(相当于接口的子类)来 ...
- 安装完Apache后,配置httpd.conf来使apache来加载php模块
以apache模块的方式来安装php,在httpd.conf文件中首先使用LoadModule php5_module '.../php5apache2.dll'来动态装载Php模块,然后再用语句Ad ...
- Webstorm2018破解笔记
参考链接: (1)https://www.jb51.net/softs/598714.html 过程步骤 (2)http://idea.lanyus.com/ IntelliJ IDEA 注册 ...
- windows兼容方式安装python[转]
Python 是一门很不错的语言,语言简单易学,又不失脚本语言的灵活性,还有海量的第三方库,覆盖的很全面.但也有不少“硬伤”,比如 Python 2.x 和 Python 3.x 版本之间的不兼容等等 ...
- MacOS下JDK6源码配置
参考:http://www.mkyong.com/mac/how-to-download-jdk-source-code-for-mac-os-x/ 系统默认的JDK是没有源码的,据说这是因为此JDK ...
- 多线程环境下的UI异步操作
转自原文 多线程环境下的UI异步操作 解决VS中,线程间不可互操作的问题,一揽子解决方案: 一.首先,定义一个类:SetControlProperty using System.Reflection; ...
- myBaits缓存
转自:https://blog.csdn.net/zhongzh86/article/details/50019511 9. Mybatis 缓存 正如大多数持久层框架一样,MyBatis 同样提供了 ...
- Redis实战——简单介绍
出自:https://www.cnblogs.com/moonlightL/p/7364107.html Redis简单介绍 Redis是一个开源,高级的键值存储和一个适用的解决方案,用于构建高性能, ...
- Python 格式化输出 ( 颜色 )
简介: Python 中如果想让输出有颜色显示,实现起来还是挺容易的,你需要拥有 termcolor 的知识! 参考地址:https://pypi.python.org/pypi/termcolor/ ...