前言:这是算法中很经典的一道题

题目:7月17日是Mr.W的生日,ACM-THU为此要制作一个体积为NπNπ的M层生日蛋糕,每层都是一个圆柱体。

设从下往上数第i层蛋糕是半径为RiRi, 高度为HiHi的圆柱。

当i < M时,要求RiRi > RiRi+1且HiHi > HiHi+1。

由于要在蛋糕上抹奶油,为尽可能节约经费,我们希望蛋糕外表面(最下一层的下底面除外)的面积Q最小。

令Q = Sπ ,请编程对给出的N和M,找出蛋糕的制作方案(适当的RiRi和HiHi的值),使S最小。

除Q外,以上所有数据皆为正整数 。

输入格式

输入包含两行,第一行为整数N(N <= 10000),表示待制作的蛋糕的体积为NπNπ。

第二行为整数M(M <= 20),表示蛋糕的层数为M。

输出格式

输出仅一行,是一个正整数S(若无解则S = 0)。

数据范围

1≤N≤100001≤N≤10000,

1≤M≤201≤M≤20

输入样例:

100

2

输出样例:

68

题解思路:

该题是经典的爆搜剪枝问题,要求体积不变下,表面积最小(除了第一层的底面积) ,那么从每一层蛋糕的角度来看,蛋糕的半径和高度都是单调递减,从枚举每一层的半径和高度,枚举的时候有一个原则,即优先枚举 选择决策少的来扩展,半径和高度这两个变量搜索范围的确定有点意思,后面会讲解。

关于爆搜剪枝问题,剪枝当然是重中之重,该题可以提出四个剪枝方法;剪枝经常应用于深搜和广搜当中,策略就是寻找过滤条件,提前减少不必要的搜索路径。

搜索解的讨论(搜索极其重视搜索顺序,个头大的先搜索,方案数将较少):1、贪心的思想是保持每步最优解,以达到全局最优解2、爆搜如何产生最优解呢?将需要搜索顺序排成从大到小,从中进行搜索。

从蛋糕从下往上搜索,上表面积就是最下面圆的面积,求解过程注重侧面积和体积即可,

假设当前状态有 s,v,rdep+1∼m,hdep+1∼ms,v,rdep+1∼m,hdep+1∼m, dep对应的状态,有:

n−v≥r2dephdep

n−v≥rdep2hdep

有上界:

rdep=min(n−v,rdep+1−1)

rdep=min(n−v,rdep+1−1)

hdep=min(n−vr2dep,hdep+1−1)

hdep=min(n−vrdep2,hdep+1−1)

有下界:

rdep=dep,hdep=dep

rdep=dep,hdep=dep

很明显,ri=i,hi=iri=i,hi=i 是最小的情况,

它们对应的 minsi=2rihi=2i2,minvi=r2ihi=i3minsi=2rihi=2i2,minvi=ri2hi=i3

如果当前结果加最小情况超过答案,那么后面就不会有解。

在有解的情况下,有下面不等式成立:

s1∼dep−1=2∑i=1dep−1rihi,v1∼dep−1=n−v=∑i=1dep−1r2ihi

s1∼dep−1=2∑i=1dep−1rihi,v1∼dep−1=n−v=∑i=1dep−1ri2hi

ri

ri

s1∼dep−1=2∑i=1dep−1rihi=2rdep∑i=1dep−1rihirdep≥2rdep∑i=1dep−1r2ihi

s1∼dep−1=2∑i=1dep−1rihi=2rdep∑i=1dep−1rihirdep≥2rdep∑i=1dep−1ri2hi

s1∼dep−1≥2(n−v)rdep

s1∼dep−1≥2(n−v)rdep

即,2(n−v)rdep2(n−v)rdep 是后面未求面积的下限,如果 2(n−v)rdep+s2(n−v)rdep+s 大于答案,那么这样的状态是不会更优的。

作者:VMice

链接:https://www.acwing.com/solution/AcWing/content/1500/

#include

#include

#include

using namespace  std;

const int N=25,Inf=1e9;

//全局变量

int n,m;

int R[N],H[N];//每层的半径和高度

int minv[N],mins[N];

int res=Inf ; //定义初始答案为正无穷

/*

爆搜:对每层蛋糕的半径和高度进行搜索,注意更新半径和高度

*/

void dfs(int u,int v,int s)//args:当前层数、当前体积、当前表面积

{

//四个剪枝方法

if(v+minv[u]>n)return;

if(s+mins[u]>=res)return;

//最重要的优化

if(s+2*(n-v)/R[u+1]>=res)return;

if(!u)  //如果到达最上一层,输出最上一层,非常重要的一个语句,目的是使爆搜达到条件后终止

{

if(n==v)res=s;//在最后一层搜索时,主要的操作步骤是找到满足条件的解后结束

return;

}

//终于理解了为什么第u层的r,h最小半径为u,因为最顶层r,h最小为1,那么依次递增,最大层的m的r,h最小值为m

for(int r=min((int)(double)sqrt(n-v),R[u+1]-1);r>=u;r–)//枚举状态,r,h从大到小枚举,同时有范围

for(int h=min((n-v)/r/r,H[u+1]-1);h>=u;h–) //

{

//注意当最后一层确定时,要加第一层的低盘面积

int t=0;

if(u==m)t=r*r;

R[u]=r,H[u]=h;   //新知识点:更新当前的半径和高度

dfs(u-1,v+r*r*h,s+2*r*h+t);//参数更新及传递

}

}

int main()

{

//读入数据

cin>>n>>m;

//初始化minv,mins

for(int i=1;i<=m;i++)

{

// minv[i+1]=minv[i]+i*i*i;

//mins[i+1]=minv[i]+2*i*i;

minv[i]=minv[i-1]+i*i*i;

mins[i]=mins[i-1]+2*i*i;

}

//处理搜索边界#这里设置哨兵,帮助完成边界

R[m+1]=H[m+1]=Inf;//?

dfs(m,0,0);//赋初值最底下一层,初始面积为0,初始表面积为0

cout<

for(int i=0;i

{

cout<

cout<

cout<

}

return 0;

}

c++画蛋糕_生日蛋糕--C++相关推荐

  1. c++画蛋糕_【题解】生日蛋糕-C++

    Description 7月17日是Mr.W的生日,ACM-THU为此要制作一个体积为Nπ的M层生日蛋糕,每层都是一个圆柱体.设从下往上数第i(1 <= i <= M)层蛋糕是半径为Ri, ...

  2. c++画蛋糕_为什么Golang能从Java和C++嘴里抢来一块蛋糕

    不得不说go的市场切入点非常准确 go被设计出来的目标应用场景是服务器开发,而服务器端开发是c++和java的地盘,占了大部分份额,go的目标是从他们嘴里抢蛋糕 程序员选语言除了流行度以外,语言是否好 ...

  3. c++画蛋糕_poj1190 生日蛋糕 dfs

    题意:生日蛋糕有m层,总体积是V.从下向上,每一层的半径r和高度h都是递减的. 给m.v,求最小的表面积s.(不算底面接地的面积) 题目链接:poj1190 剪枝都还没加..样例输出都是错的...还没 ...

  4. c++画蛋糕_【DFS练习】【最大的蛋糕块】-C++

    这道题目是一个基本的dfs模板(?)下面日常贴一波dfs的基本模板: void dfs()//参数用来表示状态 { if(到达终点状态) { ...//根据题意添加 return; } if(越界或者 ...

  5. 用python画漂亮的生日蛋糕_一步一步最简单的最漂亮的画蛋糕

    一步一步最简单的最漂亮的画蛋糕 生日蛋糕简笔画教程(一) 1.先画一个长方形 2.在大长方形上面画一个小点的长方形 3.在顶端画上蜡烛和火焰 4.在底部画上地盘 5.画一些长短不一的波浪线 6.上色, ...

  6. 如何用python画雪人_pygame画雪人_函数与图形示例.py

    """pygame画雪人_函数与图形示例.py """ # 导入pygame模块 import pygame def draw_snowma ...

  7. 用python画雪人-pygame画雪人_函数与图形示例.py

    """pygame画雪人_函数与图形示例.py """ # 导入pygame模块 import pygame def draw_snowma ...

  8. python画蛋糕玫瑰

    这里写目录标题 情人节蛋糕 前言 准备工作 python开发工具 turtle库 进行开发 1.引入相应的库及设置画布大小.背景色 2.画蛋糕 3.画玫瑰花 效果 情人节蛋糕 前言 盼望着盼望着,2. ...

  9. python画蛋糕祝福图片_蛋糕祝福语创意幽默 创意卡通生日蛋糕图片

    下文是蜜匠婚礼网精心整理的一篇关于蛋糕祝福语创意幽默以及创意卡通生日蛋糕图片,咱们一起来看看吧,希望对你有所帮助. 一.蛋糕祝福语创意幽默 1.今天是你的生日,我小心翼翼的记录我们点滴,庆幸我们走过的 ...

  10. python画蛋糕祝福图片大全_用Python的turtle模块画生日蛋糕

    import turtle as t import math as m import random as r t.speed(10) def drawX(a, i): angle = m.radian ...

最新文章

  1. 遗传算法解决TSP问题 Python实现【160行以内代码】
  2. SAP-SAP预制凭证相关的表
  3. ICCV 2017 《Flow-Guided Feature Aggregation for Video Object Detection》论文笔记
  4. uploadify.php 漏洞,PhotoStore “uploadify.php”任意文件上传漏洞
  5. [信息安全] 1.密码工具箱
  6. Eclipse中单元测试
  7. XP远程桌面连接2008提示:远程计算机需要网络级别身份验证,而您的计算机不支持该验证...
  8. zabbix系统日志文件监控key
  9. Reddit 评级算法的工作原理
  10. 微软 Azure App Service 漏洞 NotLegit已存在4年,客户源代码被暴露
  11. 形态学操作之提取水平与垂直直线
  12. 摄像头视频画面接入,使用iframe标签嵌入到页面中(海康威视、萤石)
  13. 进度类计算_PERT
  14. java课设迷宫游戏_Java课程设计走迷宫.doc
  15. 根据身份证号和社会保险号码查询不出您的医保信息 请核实后重新填写
  16. Flannel host-gw 和 vxlan
  17. 移动的帝国:日本移动互联网兴衰启示录
  18. 诗经 - 小雅 - 出车
  19. MVC三层架构(超详细解析)
  20. 3种方法封锁BT下载 1

热门文章

  1. 认证计费系统是什么?不妨看看这篇文章
  2. 小米手机android程序闪退,小米手机软件闪退是什么原因
  3. android生成透明图片格式,Android编程实现图片透明的方法
  4. xxxx-xx-xx系统应用(周)巡检报告模版
  5. 申论(基础题)之应用文写作
  6. AI绘图之基于文本/图片制图
  7. 易课堂之算法注册机编写1
  8. 1.7 F1方程式冠军
  9. [腾讯社区开放平台]介绍开放授权协议-OAuth
  10. 策略分享-基于海龟交易模型的优化 暂存