码迷,mamicode.com
首页 > 其他好文 > 详细

CSU 1547 Rectangle(dp、01背包)

时间:2017-04-21 00:04:23      阅读:193      评论:0      收藏:0      [点我收藏+]

标签:efi   mini   题解   view   problems   cond   each   分享   ios   

题目链接:http://acm.csu.edu.cn/csuoj/problemset/problem?pid=1547

 

Description

Now ,there are some rectangles. The area of these rectangles is 1* x or 2 * x ,and now you need find a big enough rectangle( 2 * m) so that you can put all rectangles into it(these rectangles can‘t rotate). please calculate the minimum m satisfy the condition.

 

Input

There are some tests ,the first line give you the test number. 
Each test will give you a number n (1<=n<=100)show the rectangles number .The following n rows , each row will give you tow number a and b. (a = 1 or 2 , 1<=b<=100).

 

Output

Each test you will output the minimum number m to fill all these rectangles.

 

Sample Input

2
3
1 2
2 2
2 3
3
1 2
1 2
1 3

Sample Output

7
4

Hint

Source

 

题意:

  给你n个长方形(其中有宽为1的,也有宽为2的长方形),问你需要一个多大的宽为2的长方形才能将这些小长方形全部圈住(不能旋转长方形,即全部长方形为一个方向)。求最小m。

题解:

  小长方形宽为2的时候 ans+= b, 直接加。所以我们只要讨论宽为1的小长方形。

  全部的宽为1的长方形我们所要做的就是将它们分成长度尽可能接近的2堆,我们就需要用01背包来解决。

  背包的容量为sum/2(sum为全部宽为1长方形的b的和),每一个长方形的价值为b,当然重量也为b

 

技术分享
 1 #include <iostream>
 2 #include <cstdio>
 3 #include <cstring>
 4 #include <cstdlib>
 5 #include <string>
 6 #include <vector>
 7 #include <map>
 8 #include <set>
 9 #include <queue>
10 #include <sstream>
11 #include <algorithm>
12 using namespace std;
13 #define pb push_back
14 #define mp make_pair
15 #define ms(a, b)  memset((a), (b), sizeof(a))
16 //#define LOCAL
17 #define eps 0.0000001
18 typedef long long LL;
19 const int inf = 0x3f3f3f3f;
20 const int maxn = 100+10;
21 const int mod = 1000000007;
22 int w[maxn];
23 int dp[maxn*maxn];
24 void solve()
25 {
26     ms(w, 0);
27     ms(dp, 0);
28     int n, a, b, ans=0, sum = 0, cnt = 0;
29     scanf("%d", &n);
30     for(int i=0;i<n;i++){
31         scanf("%d%d", &a, &b);
32         if(a==2)    ans += b;
33         else w[++cnt] = b, sum+=b;
34     }
35     for(int i=1;i<=cnt;i++){
36         for(int v = sum/2; v>=w[i]; v--){
37                 dp[v] = max(dp[v], dp[v-w[i]]+w[i]);
38         }
39     }
40     ans += max(dp[sum/2], sum-dp[sum/2]);
41     printf("%d\n", ans);
42 }
43 int main()
44 {
45     #ifdef LOCAL
46         freopen("jumping.in", "r", stdin);
47 //      freopen("output.txt", "w", stdout);
48     #endif // LOCAL
49     int T;
50     scanf("%d", &T);
51     while(T--){
52         solve();
53     }
54     return 0;
55 }
View Code

 

总结:

1)了解到了如果将一个数堆分成最接近的2堆,可以转变成01背包。

 

 

比赛时还是靠队友过了XD。

CSU 1547 Rectangle(dp、01背包)

标签:efi   mini   题解   view   problems   cond   each   分享   ios   

原文地址:http://www.cnblogs.com/denghaiquan/p/6741491.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!