装箱问题POJ1017

目录

问题描述

 思路

代码


问题描述

 思路

        问题描述中各长方形高度是与箱子高度相同的,因此只需要考虑长和宽,即二维平面的问题。

        首先说一下总体思路:先放大的,后放小的。为什么要先放大的呢?因为题目要求求出最少的箱子数,若是箱子先放小的,那么到后面的箱子大的就放不进去,而要放入新的箱子里。若先放大的,那后面可以用小的方块填充。

下面是放方块的分析:

1.  4*4,5*5,6*6的块 单独占一个箱子

 

2.  3*3的块,每4块占一个箱子,余下的再占一个箱子

 

3.  如果箱子里放1个 3*3木块,那么还能 放5个2*2木块,以 及7个1*1木块

 

4. 如果箱子里放2个 3*3木块,那么还能 放3个2*2木块,以 及6个1*1木块

 5.  如果箱子里放3个 3*3木块,那么还能 放1个2*2木块,以 及5个1*1木块

分析一: 

  1. 6*6的木块每个占用1个新箱子;
  2. 5*5的木块每个占用1个新箱子,余下11个1*1的空格;
  3. 4*4的木块每个占用1个新箱子,余下5个2*2的空格;
  4. 3*3的木块每4个占用1个新箱子,不足4个也占1个新箱子, 分情况余下不同数目的空格;
  5. 2*2的木块先填空格,空格不足开新箱子,每9个2*2的木块 占1个新箱子;
  6. 1*1的木块先填空格,空格不足开新箱子,每36个占1个新 箱子

分析二:

设nTotal - 箱子数,b1~b6 - 1*1~6*6块个数

1) 先放好所有 6*6, 5*5, 4*4和3*3 的木块 由于每个4*4, 5*5, 6*6的木块需要单独占1个箱子; 每4个3*3的木块占1个箱子,余下的最多最少占1个箱子(这也是为什么b3要加3的原因)。

所以,它们需要的箱子总数为: nTotal = b6 + b5 + b4 + (b3+3)/4

2) 先把2*2的木块放到放有4*4木块的箱子里,在b4个箱子中可 以放b4*5个2*2的木块; 再把2*2的塞到放有3*3木块的箱子里:

设一个数组: int Contain2[4] = {0, 5, 3, 1}; Contain2[i] 表示当3*3木块的数目b3除以4的余数分别是 0,1,2,3时,会产生多少个能放2*2木块的空格。

放完2*2的木块后,再算一下有多少1*1的空格,能否把1*1 的木块都填进去,如果不能,也容易算出还要加多少个箱子。

3) 计算放好6*6, 5*5, 4*4, 3*3后留下多少空格能放2*2 c2 = 5 * b4 + Contain2[b3 % 4];

4) 在放好2*2的木块后,算留下多少空格能放1*1 c1 = 36 * nTotal - 36 * b6 - 25 * b5 - 16 * b4 - 9 * b3 - 4 * b2;

代码

#include <stdio.h>
int main( )
{
 int b6,b5,b4,b3,b2,b1; //不同大小的木块个数
 int nTotal = 0; //最少需要的箱子数目
 int c1; //当前能放 1*1 木块的空格数目
 int c2; //当前能放 2*2 木块的空格数目
 int Contain2[4] = {0, 5, 3, 1}; 
 while(1)
 {
 scanf("%d%d%d%d%d%d",&b1,&b2,&b3,&b4,&b5,&b6);
 if (b1==0 && b2==0 && b3==0 && b4==0 && b5==0 && b6==0) 
break;
 nTotal = b6 + b5 + b4 + (b3 + 3)/4;
 c2 = 5 * b4 + Contain2[b3%4];
 if (b2 > c2) nTotal += (b2 - c2 + 8 ) / 9;//9个2*2填满一个箱子
 c1 = 36 * nTotal - 36 * b6 - 25 * b5 - 16 * b4 - 9 * b3 - 4 * b2;
 if (b1 > c1) nTotal += ( b1 - c1 + 35 ) / 36;//36个1*1填满一个箱子
 printf("%d\n", nTotal);
 }
 return 0;

  • 2
    点赞
  • 14
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值