【分治基础】小车问题

问题 E(1155): 小车问题

时间限制: 1 Sec   内存限制: 64 MB

题目描述

甲、乙两人同时从A地出发要尽快同时赶到B地。出发时A地有一辆小车,可是这辆小车除了驾驶员外只能带一人。已知甲、乙两人的步行速度一样,且小于车的速度。问:怎样利用小车才能使两人尽快同时到达。

输入

第1行:3个整数分别表示AB两地的距离s,人的步行速度a,车的速度b。

输出

第1行:1个数,表示两人同时到达B地需要的最短时间。精确到小数点后4位。

样例输入

120 5 25

样例输出

9.6000


根据题意可得知,小车载其中一人一定距离后,必要返回接另一个人,使得两人耗时相同且最小。
于是,我们就不妨二分小车第一次载甲的行驶距离S’(甲乙先后顺序不影响),计算出T甲,T乙。
如果T甲>T乙,则说明小车载甲的行驶距离太短,反之则太长。
附线段图:(看不懂请自行模拟)


设v1=v人,v2=v车

由此可得 :

T甲1 = T乙1= S'/v2;

S乙1 = S'*v1/v2;

-----------------------------------------

T乙2 = (S'-S乙1)/(v1+v2)

         = (S'-S'*v1/v2)/(v1+v2)= S'*(v2-v1)/v2*(v1+v2);

S乙2 = T乙2*v1

         = S'*v1*(v2-v1)/[v2*(v1+v2)];

S乙1+S乙2 =S'*v1*(v2-v1)/[v2*(v1+v2)]+S'*v1/v2

                   = 2*S'*v1/(v1+v2);

T乙1+T乙2 = 2*S'/(v1+v2);

----------------------------------------

S乙3 = S-(S乙1+S乙2)

         = [S*(v1+v2)-2*S'v1]/(v1+v2);

T乙3 = S乙3/v2

         =[s*(v1+v2)-2*S'v1]/[v2*(v1+v2)];

T甲2+T甲3 = (S-S')/v1;

 

故:

T甲总 = S'/v2+(S-S')/v1;

T乙总 = T乙1+T乙2+T乙3

          = [2*S'*(v2-v1)+S*(v1+v2)]/[v2*(v1+v2)];



下附二分代码:
<pre name="code" class="cpp">#include<cstdio>
#include<iostream>
#include<cstring>
#include<cmath>
#include<cstdlib>
#include<algorithm>
#include<queue>
using namespace std;

#define MAXN 100
#define MAXM
#define LL long long
#define INF 0x3f3f3f3f

double S,v1,v2;
int main()
{
	scanf("%lf%lf%lf",&S,&v1,&v2);
	double l=0,r=S,mid,t1,t2;
	while(r-l>=0.0001)
	{
		mid=(l+r)/2;
		t1=mid/v2+(S-mid)/v1;
		t2=(2*mid*(v2-v1)+S*(v1+v2))/(v2*(v1+v2));
		if(t1>t2)l=mid;
		else r=mid;
	}
	
	printf("%0.4lf\n",l/v2+(S-l)/v1);
}
 
 

又根据T甲=T乙

可列方程:

S'/v2+(S-S')/v1= [2*S'*(v2-v1)+S*(v1+v2)]/[v2*(v1+v2)];

解得:

S'=S*(v2*v2-v1*v1)/(2*v1*v2-3*v1*v1+v2*v2);

T= S'/v2+(S-S')/v1;

 

下附代码:

<pre name="code" class="cpp">#include<cstdio>
#include<iostream>
#include<cstring>
#include<cmath>
#include<cstdlib>
#include<algorithm>
#include<queue>
using namespace std;
 
#define MAXN 100
#define MAXM
#define LL long long
#define INF 0x3f3f3f3f
 
double S,v1,v2;
int main()
{
    scanf("%lf%lf%lf",&S,&v1,&v2);
    double stmp=S*(v2*v2-v1*v1)/(2*v1*v2-3*v1*v1+v2*v2);
    printf("%0.4lf\n",stmp/v2+(S-stmp)/v1);
}
 
 
这两种方法码完后人都不好了,尤其是公式推错了好几次。。。数学不好是硬伤啊。

评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值