【bzoj1502】[NOI2005]月下柠檬树 自适应Simpson积分
题目描述
![](http://www.lydsy.com/JudgeOnline/upload/201802/111.png)
输入
输出
输出1个实数,表示树影的面积。四舍五入保留两位小数。
样例输入
2 0.7853981633
10.0 10.00 10.00
4.00 5.00
样例输出
171.97
题解
自适应Simpson积分
根据数学知识:在平行光投影下,圆的半径保持不变,位置为 高度/tanα ;圆台/圆锥的侧面投影为两圆/一圆一点的外公切线。
那么先将圆的位置求出,然后依次求相邻两圆公切线并将线段记录,此时注意内切/内含的两个圆是没有外公切线的。这里求公切线使用了射影定理。
如下图:
其中黑色的是投影后的圆,红色的是公切线段。
那么我们要求的就是最外层轮廓所围成的图形的面积。由于对称性因此只需要求出上半部分然后乘2。
注意到上半部分的外层轮廓形成了连续的一段函数,因此考虑使用自适应Simpson积分来求面积。
Simpson积分:对于三次及以下多项式函数,有 $\int_l^rf(x)dx=(r-l)·\frac {f(l)+f(r)+4f(\frac{l+r}2)}6$ 。
自适应Simpson积分:对于任意连续函数 $f(x)$ 求 $\int_l^rf(x)dx$,先将其当作三次函数使用Simpson积分求出 $[l,r]$ 、$[l,mid]$ 和 $[mid+r]$ 的面积,如果左半部分和右半部分面积之和与总面积之差满足精度要求则返回,否则递归左右并求和作为总面积。
本质上相当于插一个三次函数,如果差得比较多则递归左右。
回过头来看本题,问题变为:给出 $x$ ,求 $f(x)$ 。显然可以在每个圆和每条线段上(如果存在)求出 $x$ 的函数值,取最大值即为 $f(x)$ 。
注意精度要设得小一些,因为求和的部分使误差增大。
时间复杂度 $O(跑得过)$ 。
#include <cmath>
#include <cstdio>
#include <algorithm>
#define N 510
#define eps 1e-5
using namespace std;
struct circle
{
double x , r;
}c[N];
struct line
{
double x1 , y1 , x2 , y2;
}l[N];
double h[N];
int n , m;
inline double squ(double x)
{
return x * x;
}
inline double f(double p)
{
int i;
double ans = 0;
for(i = 1 ; i <= n ; i ++ )
if(p >= c[i].x - c[i].r && p <= c[i].x + c[i].r)
ans = max(ans , sqrt(squ(c[i].r) - squ(p - c[i].x)));
for(i = 1 ; i <= m ; i ++ )
if(p >= l[i].x1 && p <= l[i].x2)
ans = max(ans , l[i].y1 + (p - l[i].x1) * (l[i].y2 - l[i].y1) / (l[i].x2 - l[i].x1));
return ans;
}
inline double calc(double l , double r)
{
return (r - l) * (f(l) + f(r) + f((l + r) / 2) * 4) / 6;
}
double simpson(double l , double r , double s)
{
double mid = (l + r) / 2 , x = calc(l , mid) , y = calc(mid , r);
if(fabs(x + y - s) <= eps) return s;
return simpson(l , mid , x) + simpson(mid , r , y);
}
int main()
{
int i;
double alpha , t , L = 1e9 , R = -1e9;
scanf("%d%lf" , &n , &alpha) , n ++ ;
for(i = 1 ; i <= n ; i ++ ) scanf("%lf" , &h[i]) , h[i] += h[i - 1] , c[i].x = h[i] / tan(alpha);
for(i = 1 ; i < n ; i ++ ) scanf("%lf" , &c[i].r);
for(i = 1 ; i < n ; i ++ )
{
if(c[i + 1].x - c[i].x > fabs(c[i + 1].r - c[i].r))
{
m ++ ;
t = c[i].r * (c[i].r - c[i + 1].r) / (c[i + 1].x - c[i].x) , l[m].x1 = c[i].x + t , l[m].y1 = sqrt(squ(c[i].r) - squ(t));
t = c[i + 1].r * (c[i].r - c[i + 1].r) / (c[i + 1].x - c[i].x) , l[m].x2 = c[i + 1].x + t , l[m].y2 = sqrt(squ(c[i + 1].r) - squ(t));
}
}
for(i = 1 ; i <= n + 1 ; i ++ ) L = min(L , c[i].x - c[i].r) , R = max(R , c[i].x + c[i].r);
printf("%.2lf\n" , 2 * simpson(L , R , calc(L , R)));
return 0;
}
【bzoj1502】[NOI2005]月下柠檬树 自适应Simpson积分的更多相关文章
- [BZOJ 1502] [NOI2005] 月下柠檬树 【Simpson积分】
题目链接: BZOJ - 1502 题目分析 这是我做的第一道 Simpson 积分的题目.Simpson 积分是一种用 (fl + 4*fmid + fr) / 6 * (r - l) 来拟合 fl ...
- [BZOJ1502]月下柠檬树(自适应辛普森积分)
1502: [NOI2005]月下柠檬树 Time Limit: 5 Sec Memory Limit: 64 MBSubmit: 1387 Solved: 739[Submit][Status] ...
- [日常摸鱼]bzoj1502[NOI2005]月下柠檬树-简单几何+Simpson法
关于自适应Simpson法的介绍可以去看我的另一篇blog http://www.lydsy.com/JudgeOnline/problem.php?id=1502 题意:空间里圆心在同一直线上且底面 ...
- BZOJ 1502 月下柠檬树(simpson积分)
题目链接:http://61.187.179.132/JudgeOnline/problem.php?id=1502 题意:给出如下一棵分层的树,给出每层的高度和每个面的半径.光线是平行的,与地面夹角 ...
- BZOJ1502: [NOI2005]月下柠檬树
Simpson法相当好用啊!神奇的骗分算法! /************************************************************** Problem: 1502 ...
- bzoj 1502 月下柠檬树【Simpson积分】
投影到地面之后,会发现圆形在平行光下面积和形状是不会变的,也就是所要求的图形是若干个圆和把相邻两个圆连起来的公切线所组成的. 公切线和圆间距瞎求一下就行,注意要去掉被完全覆盖的圆 然后simpson即 ...
- 【BZOJ1502】[NOI2005]月下柠檬树 Simpson积分
[BZOJ1502][NOI2005]月下柠檬树 Description 李哲非常非常喜欢柠檬树,特别是在静静的夜晚,当天空中有一弯明月温柔地照亮地面上的景物时,他必会悠闲地坐在他亲手植下的那棵柠檬树 ...
- 【BZOJ-1502】月下柠檬树 计算几何 + 自适应Simpson积分
1502: [NOI2005]月下柠檬树 Time Limit: 5 Sec Memory Limit: 64 MBSubmit: 1017 Solved: 562[Submit][Status] ...
- BZOJ 1502: [NOI2005]月下柠檬树 [辛普森积分 解析几何 圆]
1502: [NOI2005]月下柠檬树 Time Limit: 5 Sec Memory Limit: 64 MBSubmit: 1070 Solved: 596[Submit][Status] ...
随机推荐
- OpenStack入门篇(一)之云计算的概念
1.云计算 云计算是一种按使用量付费的模式,这种模式提供可用的.便捷的.按需的网络访问, 进入可配置的计算资源共享池(资源包括网络,服务器,存储,应用软件,服务),这些资源能够被快速提供,只需投入很少 ...
- linux设置定时任务调用接口
1.设置目录 cd /var/spool/cron 2.编辑文件(当前登录用户,不一定是root) vim root 3.添加内容 0 0 * * * wget http://192.144.141. ...
- Maven学习(十二)-----Maven POM
Maven POM POM代表项目对象模型.它是 Maven 中工作的基本单位,这是一个 XML 文件.它始终保存在该项目基本目录中的 pom.xml 文件.POM 包含的项目是使用 Maven 来构 ...
- MySQL数据库之安装,基本操作
一.基础部分 1.数据库是什么 之前所学,数据要永久保留,比如用户注册的用户信息,都是保存于文件,而文件只能存在于某一台机器上. 如果我们不考虑从文件中读取数据的效率问题,并且假设我们的程序所有的组件 ...
- shell 判断日期间隔及润年
#!/bin/bash test.sh until echo "----------------------------------" echo "请输入您的选择:&qu ...
- Vue学习计划基础笔记(三)-class与style绑定,条件渲染和列表渲染
Class与style绑定.条件渲染和列表渲染 目标: 熟练使用class与style绑定的多种方式 熟悉v-if与v-for的用法,以及v-if和v-for一起使用的注意事项 class与style ...
- spark重点知识
1 scala 2 spark rdd 3 sprak core 4 性能优化 5 spark sql 6 spark streaming 掌握程度-精通的理解:
- vue2.0做移动端开发用到的相关插件和经验总结1.0
最近在用vue2.0做微信公众号相关的前端开发,经过这次开发实践,现将项目中用到的相关比较实用的插件及遇到的相关问题进行整理,希望和大家共同交流...... cssrem:一个CSS值转REM的VSC ...
- PLSQL变量和类型,流程控制语句,集合
---PLSQL 调试授权 GRANT debug any procedure, debug connect session TO scott; --定义变量 declare part_number ...
- 洛谷【P1057】传球游戏
https://www.luogu.org/problemnew/show/P1057 题目描述 在体育课上, 老师带着同学们一起做传球游戏. 游戏规则是这样的: n 个同学站成一个圆圈, 其中的一个 ...