LA3905流星
题意:
在一个二维平面上有n个流星,每个流星有自己的初始位置和速度,有一个照相机,张相机的可视范围是一个矩形框,左下角(0,0)右上角(w ,h),然后问你相机的矩形内出现的最多的流星数是多少?
思路:
感觉是一道很不错的题目,想到流星数目,第一反应就是可以把他转化成时间段,我们求出每个流星的进入相机时间,和出相机时间,这样就会得到一个时间段,流星的最大
数量也就是时间段的最大重叠部分,这个不解释了应该不难理解,现在问题就来了,我们怎么求得所有的时间段呢?一开始我也感觉很麻烦,然后在白书上学了一个比较方便的方法,我们求时间段可以先把流星分解了,x,y单独算,进入的时间肯定是进x进y的最大值,出去的时间肯定是出x,出y的最小值,这样我们分别求完之后就ok了,如果L>=R就证明没有在相机范围内出现过,下面给出求L,R的代码
void Update(int x ,int a ,int w ,double& L ,double& R)
{
if(a == 0)
{
if(x <= 0 || x >= w) R = L - 1; //永远也进步了相机
}
else if(a > 0)//往上跑
{
L = Max(L ,-(double)x / a);
R = Min(R ,(double)(w - x) / a);
}
else//往下跑
{
L = Max(L ,(double)(w - x) / a);//理解不了的注意这里的a是负的
R = Min(R ,-(double)x / a);
}
}
求x,y的时候都是用的上面的那个,只不过传的参数不一样罢了,具体细节可以看代码。
这样我们就得到了所有流星的时间段L,R(L>=R的是不满足的,直接丢弃),然后就是求区间的最大重叠面积了,这个也比较好求,如果你不嫌麻烦可以写线段树贪心去求,时间复杂度是O(n*log(n))的,不过有一个更省事更快的方法,就是扫面线法O(n)<其实这么说有漏洞,因为扫描线涉及到排序,排序是O(n*log(n))的,这个地方大家知道就行了>,我们可以把所有端点都扔进结构体数组里,然后按照时间从小到大排序,如果时间相等那么就后端点在前面(这样的原因是题目中说在相机边框上的不算,如果算的话就入端点在前面),排序之后直接扫一遍,遇到前端点就++,后端点就--,过程中最大的值就是答案,这个应该很好理解,不理解的在纸上画一画,每次变化的时候都是在端点上变化的,这个就是经典的扫描线想法,扫描线也可以配合着线段树应用,求重叠面积,体积,周长啥的。这个题目还有一个小小的优化(白书上说的),我们可以躲开浮点运算,因为整个程序里涉及到的除法就是除以速度,速度的范围是绝对值<=10,那么我们直接把被除数扩大1,2,3..10的最小公倍数2520倍就行了,这样保证都是整除,至于为什么我想不用我解释了。
#include<stdio.h>
#include<string.h>
#include<algorithm>
#define N 100000 + 10
using namespace std;
typedef struct
{
int mk;
double time;
}NODE;
NODE node[N+N];
bool camp(NODE a ,NODE b)
{
return a.time < b.time || a.time == b.time && a.mk < b.mk;
}
double Max(double x ,double y)
{
return x > y ? x : y;
}
double Min(double x ,double y)
{
return x < y ? x : y;
}
void Update(int x ,int a ,int w ,double& L ,double& R)
{
if(a == 0)
{
if(x <= 0 || x >= w) R = L - 1;
}
else if(a > 0)
{
L = Max(L ,-(double)x / a);
R = Min(R ,(double)(w - x) / a);
}
else
{
L = Max(L ,(double)(w - x) / a);
R = Min(R ,-(double)x / a);
}
}
int main ()
{
int t ,w ,h ,n ,i;
int x ,y ,a ,b;
scanf("%d" ,&t);
while(t--)
{
scanf("%d %d" ,&w ,&h);
scanf("%d" ,&n);
int nowid = 0;
for(i = 1 ;i <= n ;i ++)
{
scanf("%d %d %d %d" ,&x ,&y ,&a ,&b);
double L = 0 ,R = 999999999;
Update(x ,a ,w ,L ,R);
Update(y ,b ,h ,L ,R);
if(L < R)
{
node[++nowid].time = L;
node[nowid].mk = 1;
node[++nowid].time = R;
node[nowid].mk = -1;
}
}
int Ans = 0;
sort(node + 1 ,node + nowid + 1 ,camp);
int sum = 0;
for(i = 1 ;i <= nowid ;i ++)
{
sum += node[i].mk;
if(Ans < sum) Ans = sum;
}
printf("%d\n" ,Ans);
}
return 0;
}
//排除浮点型运算
void Update(int x ,int a ,int w ,int& L ,int& R)
{
if(a == 0)
{
if(x <= 0 || x >= w) R = L - 1;
}
else if(a > 0)
{
L = Max(L ,-x * 2520 / a);
R = Min(R ,(w - x) * 2520 / a);
}
else
{
L = Max(L ,(w - x) * 2520/ a);
R = Min(R ,-x * 2520/ a);
}
}
LA3905流星的更多相关文章
- canvas流星月亮星星银河
这是页面的特效,首先月亮直接出现,然后星星和银河渐渐的出现(一闪一闪),最后流星划过,留下完美的句点. 所有的动画都是通过帧来实现的. 星星的代码分为2部分,首先是随机生成星星,然后是绘制星星,最后是 ...
- iOS - CAEmitterLayer流星
效果图: 流星: #pragma mark - loading animation - (void)showLoadingAnimation { CGRect mainBounds = [[UIScr ...
- 【原创】java 流星划过天空
import java.awt.Color; import java.awt.Graphics; import java.awt.image.BufferedImage; import javax.s ...
- TurnipBit口袋编程计算机:和孩子一起DIY许愿的流星
听说对着流星许愿,许的愿望都会实现,虽然不知道这个说法是不是真的,但是流星还是很好看的,为了能一直看到流星,今天就自己做一个流星保存下来,想什么时候看,就什么时候看. 首先需要想象一下流星是什么样子的 ...
- 5.HTML+CSS制作一颗流星
效果地址:https://codepen.io/flyingliao/pen/pBzKbZ HTML code: <div class="sky"> <span& ...
- LA3905
题意: 给出n颗流星,第i颗在第T秒时飞到(xi+ai*t,yi+bi*t),给出一个矩形,问在某一时刻这个矩形中的流星数目最多有多少 题解: 首先计算出每一颗流星经过时间 然后左端点移动,计算出少了 ...
- 6 cocos2dx粒子效果,类图关系,系统原生粒子和自己定义粒子效果,粒子编译器软件,爆炸粒子效果,烟花效果,火焰效果,流星效果,漩涡粒子效果,雪花效果,烟雾效果,太阳效果,下雨效果
1 粒子 演示样例 2 类图关系 3 系统原生粒子 CCParticleSystem 全部粒子系统的父类 CCParticleSystemPoint. CCParticleSystemQuad ...
- LA-3905 (扫描线)
题意: 给一些流星的初始位置和运动向量,给了相机的拍摄范围;问你最多能拍到多少颗流星; 思路: 将流星用出现在相机拍摄范围内的时间段表示;sort后在扫面端点更新最大值; Ac代码: #include ...
- Win10《芒果TV》更新v3.8.30流星版:优化稳定性、升级无边框播放体验
随着暑假到来,大波王牌综艺和青春电视剧热浪来袭,Win10版<芒果TV>全平台同步更新流星版v3.8.30,进一步提升稳定性,巩固播放体验,升级剧场模式和画中画无边框体验,我们在芒果等你. ...
随机推荐
- C# 应用 - 封装类访问 Mysql 数据库
个人经历的项目主要都是用 Postgresql 或 Oracle 数据库,本文非原创,从他处整理而来. 1. 库类 mysql.data.dll using MySql.Data.MySqlClien ...
- Hibernate Validator异常HV000221解决办法
自建博客地址:https://www.bytelife.net,欢迎访问! 本文为博客同步发表文章,为了更好的阅读体验,建议您移步至我的博客 本文作者: Jeffrey 本文链接: https://w ...
- python matrix转list
a = [[1,2],[3,4]] a = np.mat(a) print(a.getA().tolist())
- go语言几个最快最好运用最广的web框架比较
比较一下常用的golang web框架 令人敬畏的Web框架 如果你为自己设计一个小应用程序,你可能不需要一个Web框架,但如果你正在进行生产,那么你肯定需要一个,一个好的应用程序. 虽然您认为自己拥 ...
- Salesforce LWC学习(三十二)实现上传 Excel解析其内容
本篇参考:salesforce lightning零基础学习(十七) 实现上传 Excel解析其内容 上一篇我们写了aura方式上传excel解析其内容.lwc作为salesforce的新宠儿,逐渐的 ...
- P1014_Cantor表 (JAVA语言)
题目描述 现代数学的著名证明之一是Georg Cantor证明了有理数是可枚举的.他是用下面这一张表来证明这一命题的: 1/11/1 , 1/21/2 , 1/31/3 , 1/41/4, 1/51/ ...
- Python3 使用requests请求,解码时出错:'utf8' codec can't decode byte 0x83 in position 1: invalid start byte
requests请求的响应内容能够通过几个属性获得: response.text 为解码之后的内容,解码会根据响应的HTTP Header中的Content-Type选择字符集.例如 1 " ...
- C#修改AD账号及密码
在使用AD域环境搭建的账号系统修改密码的时候比较麻烦一般需要管理员在域环境去进行对用户的密码进行修改. 以下就是用来查询和修改AD域密码的方法. 1 /// <summary> 2 /// ...
- oo第四单元与课程总结
Part1 本单元三次作业架构设计总结 1.组织结构 由于官方代码中已经给我们提供了许多零散的类元素,如UmlClass``UmlAssociation``UmlParameter等,因此我首先将某些 ...
- windows上phpstudy配置memcache
原文 http://blog.csdn.net/ltx06/article/details/78588448 总的来说,分两步:同时安装memcached软件服务和安装php_memcache ...