(三分)Turn the corner -- HDOJ

来源:互联网 发布:云计算最大的特征是() 编辑:程序博客网 时间:2024/06/07 08:36

Turn the corner
Time Limit: 3000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 722 Accepted Submission(s): 329

Problem Description
Mr. West bought a new car! So he is travelling around the city.

One day he comes to a vertical corner. The street he is currently in has a width x, the street he wants to turn to has a width y. The car has a length l and a width d.

Can Mr. West go across the corner?

Input
Every line has four real numbers, x, y, l and w.
Proceed to the end of file.

Output
If he can go across the corner, print “yes”. Print “no” otherwise.

Sample Input

10 6 13.5 4
10 6 14.5 4

Sample Output

yes
no

Source
2008 Asia Harbin Regional Contest Online

Recommend
gaojie

总结:
三分适用于在一个区间内,求凸函数或者凹函数 的最值,二分适用于单调的函数。

难点:
1、要想顺利通过,必须保证A点到Z轴的距离H 小于等于y
2、H的求解
这里写图片描述
3、H函数的单调性
函数 = (l*sin(t) - x) / tan(t) + d / sin(t);

    l = x = d = 3;;        for(double i=0.1; i<=PI/2.0; i += 0.1)        {           cout << Cal(i)<<endl;        }

运行上面的代码,可以看到值是先增大后减小,可以断定函数先增后减,找出最大值,再与y进行比较,就可以得出答案

#include<iostream>#include<string.h>#include<string>#include<stdio.h>#include<algorithm>#include<math.h>#define PI acos(-1.0)#define eps 0.000001using namespace std;double x,y,l,d;double Cal(double t){    return (l*sin(t) - x) / tan(t) + d / sin(t);}int main(void){ //   freopen("in.txt","r",stdin);    while(scanf("%lf %lf %lf %lf",&x,&y,&l,&d) != EOF )    {        double midl,midr,l,r,y1,y2;        l = 0,r = 0.5*PI;        while((fabs(r-l) > eps))        {            midl = l + (r-l)/3;            midr = r - (r-l)/3;            y1 = Cal(midl);            y2 = Cal(midr);            if(y1 > y2)                r = midr;            else                l = midl;        }        if(Cal(r) <= y) cout << "yes";        else cout << "no";        cout <<endl;    }    /*        l = x = d = 3;;        for(double i=0.1; i<=PI/2.0; i += 0.1)        {           cout << Cal(i)<<endl;        }*/    return 0;}
原创粉丝点击