[洛谷P2571] [SCOI2010]传送带
题目描述
在一个2维平面上有两条传送带,每一条传送带可以看成是一条线段。两条传送带分别为线段AB和线段CD。lxhgww在AB上的移动速度为P,在CD上的移动速度为Q,在平面上的移动速度R。现在lxhgww想从A点走到D点,他想知道最少需要走多长时间
输入输出格式
输入格式:
输入数据第一行是4个整数,表示A和B的坐标,分别为Ax,Ay,Bx,By
第二行是4个整数,表示C和D的坐标,分别为Cx,Cy,Dx,Dy
第三行是3个整数,分别是P,Q,R
输出格式:
输出数据为一行,表示lxhgww从A点走到D点的最短时间,保留到小数点后2位
输入输出样例
输入样例#1:
0 0 0 100
100 0 100 100
2 2 1
输出样例#1:
136.60
说明
对于100%的数据,1<= Ax,Ay,Bx,By,Cx,Cy,Dx,Dy<=1000, 1<=P,Q,R<=10
Brave_Cattle sto backup_noob orz Brave_Cattle
backup_noob帮助Brave_Cattle调好了参数让暴力通过了此题.
一句话题意: 一个\(1000*1000\)的矩形中有\(A,B,C,D\)四个点.并且现在你在\(A\)点,要前往\(D\)点,并且在\(AB,CD\)上有传送带,在\(AB\),平地,\(CD\)上的速度分别为P,Q,R.问到达\(D\)的最小时间.
题解: 首先考虑在矩形中行进的路径.如果不走传送带,显然是直接走直线距离最短,如果要走传送带,也是直线上传送带需要走的平地路径最短.那么显然最终走的总距离就是\(A\)->\(AB\)上一点->\(CD\)上一点->\(D\).那么我们可以通过枚举得到\(AB,CD\)上这一点的位置,也就是将\(AB\)看作一个向量,则\(\vec {AP}=k*\vec {AB}, k∈[0,1]\),其中\(P\)为\(AB\)上的位置.因为本题精度要求不高,所以这样枚举是可以过的.
当然这题还有模拟退火,三分等算法.
// luogu-judger-enable-o2
#include<bits/stdc++.h>
using namespace std;
const double delta = 2e-4;
const int inf = 2147483647;
double ans = inf, P, Q, R;
struct point{
double x, y;
}a[10];
inline double dis(point a, point b){
return sqrt((a.x-b.x)*(a.x-b.x)+(a.y-b.y)*(a.y-b.y));
}
inline point get_pos(point a, point b, double k){
point temp; temp.x = (b.x-a.x)*k+a.x, temp.y = (b.y-a.y)*k+a.y;
return (point){ (b.x-a.x)*k+a.x, (b.y-a.y)*k+a.y };
}
inline double calc(double i, double j){
point temp1 = get_pos(a[1], a[2], i), temp2 = get_pos(a[3], a[4], j);
return dis(a[1], temp1)/P+dis(temp1, temp2)/R+dis(temp2, a[4])/Q;
}
int main(){
// freopen("walk.in", "r", stdin);
// freopen("walk.out", "w", stdout);
cin >> a[1].x >> a[1].y >> a[2].x >> a[2].y >> a[3].x >> a[3].y >> a[4].x >> a[4].y;
cin >> P >> Q >> R;
for(double i=0;i<=1;i+=delta)
for(double j=0;j<=1;j+=delta) ans = min(ans, calc(i, j));
cout << fixed << setprecision(2) << ans << endl;
return 0;
}
当然这题是可以用三分来做的.因为从一条直线到另一条直线的时间满足一个凸函数的性质.可以感性的理解一下:到直线的一端的无穷远的地方需要无限的时间,到另一端无穷远的地方也要无限时间,而到中间一个位置可以使时间最小,所以可以三分.
所以这里可以用一个三分套三分的方法,先三分在\(AB\)段走的长度,再三分在\(CD\)段走的长度.(虽然这里为什么三分套三分仍然是一个凸函数我并不是很懂,但是至少也可以枚举一边走的长度然后三分另一边).大概实现看一下代码吧.
#include<bits/stdc++.h>
using namespace std;
const double eps = 1e-6;
double P, Q, R;
struct point{
double x, y;
}a[10];
inline double dis(point a, point b){
return sqrt((a.x-b.x)*(a.x-b.x)+(a.y-b.y)*(a.y-b.y));
}
inline point get(point a, point b, double k){
return (point){ (b.x-a.x)*k+a.x, (b.y-a.y)*k+a.y };
}
inline double calc(double k1, double k2){
point temp1 = get(a[1], a[2], k1), temp2 = get(a[3], a[4], k2);
return dis(a[1], temp1)/P+dis(temp1, temp2)/R+dis(temp2, a[4])/Q;
}
inline double check(double k){
double l = 0, r = 1;
while(r-l > eps){
double p1 = (2*l+r)/3, p2 = (l+2*r)/3;
if(calc(k, p1) > calc(k, p2)) l = p1;
else r = p2;
}
return calc(k, l);
}
int main(){
//freopen("data.in", "r", stdin);
cin >> a[1].x >> a[1].y >> a[2].x >> a[2].y;
cin >> a[3].x >> a[3].y >> a[4].x >> a[4].y;
cin >> P >> Q >> R;
double l = 0, r = 1;
while(r-l > eps){
double p1 = (2*l+r)/3, p2 = (l+2*r)/3;
if(check(p1) > check(p2)) l = p1;
else r = p2;
}
cout << fixed << setprecision(2) << check(l) << endl;
return 0;
}
[洛谷P2571] [SCOI2010]传送带的更多相关文章
- 【解题报告】洛谷 P2571 [SCOI2010]传送带
[解题报告]洛谷 P2571 [SCOI2010]传送带今天无聊,很久没有做过题目了,但是又不想做什么太难的题目,所以就用洛谷随机跳题,跳到了一道题目,感觉好像不是太难. [CSDN链接](https ...
- 洛谷P2571 [SCOI2010]传送带 [三分]
题目传送门 传送带 题目描述 在一个2维平面上有两条传送带,每一条传送带可以看成是一条线段.两条传送带分别为线段AB和线段CD.lxhgww在AB上的移动速度为P,在CD上的移动速度为Q,在平面上的移 ...
- 洛谷 P2571 [SCOI2010]传送带 题解
每日一题 day51 打卡 Analysis 这道题是用非常恶心的三分套三分做的,有一个技巧是不要枚举坐标,枚举两条线段构成三角形的相似比就好了. 了解思路就还挺好写的(尽管我还调了三天) #incl ...
- P2571 [SCOI2010]传送带
P2571 [SCOI2010]传送带 三分套三分. 前提条件:P3382 [模板]三分法 三分,求区间内单峰函数的最大/最小值. 我们把两条线段都跑三分,先ab后cd,求出最小值. 可以直接将二维坐 ...
- P2571 [SCOI2010]传送带——hyl天梦
P2571 [SCOI2010]传送带题解----天梦 如写的不好,请多见谅. 对于这道题,我首先想说,确实困惑了我好久,看网上的各种题解,却都不尽人意,思路早已明白,却不会操作.最后想想,还是觉得自 ...
- BZOJ1856或洛谷1641 [SCOI2010]生成字符串
BZOJ原题链接 洛谷原题链接 可以将\(1\)和\(0\)的个数和看成是\(x\)轴坐标,个数差看成\(y\)轴坐标. 向右上角走,即\(x\)轴坐标\(+1\),\(y\)轴坐标\(+1\),表示 ...
- BZOJ1855或洛谷2569 [SCOI2010]股票交易
一道单调队列优化\(DP\) BZOJ原题链接 洛谷原题链接 朴素的\(DP\)方程并不难想. 定义\(f[i][j]\)表示到第\(i\)天,手上持有\(j\)股时的最大收益. 转移方程可以分成四个 ...
- 洛谷 P1641 [SCOI2010]生成字符串
洛谷 这题一看就是卡塔兰数. 因为\(cnt[1] \leq cnt[0]\),很显然的卡塔兰嘛! 平时我们推导卡塔兰是用一个边长为n的正方形推的, 相当于从(0,0)点走到(n,n)点,向上走的步数 ...
- 洛谷 P1640 [SCOI2010]连续攻击问题
洛谷 一句话题意: 每个武器有两种属性,每种武器只能选择一种属性,从属性1连续递增才算攻击,求最大连续攻击次数. 因为同学告诉我这是二分图最大匹配,自然就往那个方向去想. 那么怎么建图呢? 每个武器只 ...
随机推荐
- Hero In Maze(BFS广搜)
Description 500年前,Jesse是我国最卓越的剑客.他英俊潇洒,而且机智过人^_^.突然有一天,Jesse心爱的公主被魔王困在了一个巨大的迷宫中.Jesse听说这个消息已经是两天以后了, ...
- python 项目配置虚拟环境
# Windows 环境1, 安装 Visual C++ 2015 Build Tools, 依赖.Net Framework 4.6, 安装包位置 ./tools/windows/visualcpp ...
- (beta冲刺5/7)
团队信息 队名:爸爸饿了 组长博客:here 作业博客:here 组员情况 组员1(组长):王彬 过去两天完成了哪些任务 推进后端完成安卓端接口的开发 在测试中发现返回地图接口存在错误(待修复) 推进 ...
- 深入理解Java对象序列化(转载)
原文地址:http://developer.51cto.com/art/201202/317181.htm 1. 什么是Java对象序列化 Java平台允许我们在内存中创建可复用的Java对象,但一般 ...
- lintcode-187-加油站
187-加油站 在一条环路上有 N 个加油站,其中第 i 个加油站有汽油gas[i],并且从第_i_个加油站前往第_i_+1个加油站需要消耗汽油cost[i]. 你有一辆油箱容量无限大的汽车,现在要从 ...
- <Android>spinner/AutoCompleteTextView绑定适配器
position = (Spinner)findViewById(R.id.position); String[] str = {"CEO","CFO",&qu ...
- Unity3d学习日记(二)
跟着教程做让背景可以滚动起来并添加了背景的粒子特效,加入了敌机. ctrl攻击,↑↓←→移动,Game Over后按R重新开始游戏. Space Shooter游戏地址:http://ya ...
- C# 反射与dynamic最佳组合
在 C# 中反射技术应用广泛,至于什么是反射.........你如果不了解的话,请看下段说明,否则请跳过下段.广告一下:喜欢我文章的朋友请关注一下我的blog,这也有助于提高本人写作的动力. 反射:当 ...
- MAC搭建 PHP 环境
安装homebrew homebrew是mac下非常好用的包管理器,会自动安装相关的依赖包,将你从繁琐的软件依赖安装中解放出来. 安装homebrew也非常简单,只要在终端中输入11: 1 ruby ...
- 第24天:js-函数变量声明提升
一.函数声明1.自定义函数function fun1(){ alert("我是自定义函数");}fun2();//函数不调用,自己不执行2.直接量声明var fun2=functi ...