CF 578A A Problem about Polyline

题意:
There is a polyline going through points (0, 0) – (x, x) – (2x, 0) – (3x, x) – (4x, 0) – ... - (2kx, 0) – (2kx + x, x) – ....

We know that the polyline passes through the point (a, b). Find minimum positive value x such that it is true or determine that there is no such x.

Input
Only one line containing two positive integers a and b (1 ≤ a, b ≤ 109).

Output
Output the only line containing the answer. Your answer will be considered correct if its relative or absolute error doesn't exceed 10 - 9. If there is no such x then output  - 1 as the answer.

思路:先大概确定范围,再二分。

代码:

#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<queue>
#include<algorithm>
#include<cmath>
#include<map>
using namespace std;
#define INF 0x7fffffff

int main(){
	int a,b,x,y;
	double ans = INF;
	while(scanf("%d%d",&x,&y) == 2){
		if(y > x){
			printf("-1
");
			continue;
		}
		else if(y == 0){
			printf("0.000000000001
");
			continue;
		}
		b = x+y;
		int k = 1;
		int t ;
		ans = INF ;
		for(; ;){
			t = k;
			k *= 2;
			if(b*1.0/k >= y)
			    ans = ans < b*1.0/k ? ans : b*1.0/k ;
			else
			    break;
		}
			while(t<k){
				int mid = (t+k)/2;
				if(mid%2 == 1)
				    break;
				if(b*1.0/mid >= y)
				    t = mid ;
				else
				    k = mid ;
			}
			if(t == 1)
			    t = 2;
			if(k == 1)
			    k = 2; 
			double s1 = b*1.0/k;
			double s2 = b*1.0/t;
			if(s1 >= y && s2 >= y)
			    ans = s1 > s2 ? s2 : s1 ;
			else if(s1 >= y)
			    ans = s1;
			else 
			    ans = s2;
		
		b = y -x ;
		if(b<0)
		    b = -b;
		if(b == 0){
			printf("%.12lf
",(double)y);
			continue;
		}
		k = 1;
		for(; ;){
			t = k;
			k *= 2;
			if(b*1.0/k >= y)
			    ans = ans < b*1.0/k ? ans : b*1.0/k ;
			else
			    break;
		}
		while(t<k){
				int mid = (t+k)/2;
				if(mid%2 == 1)
				    break;
				if(b*1.0/mid >= y)
				    t = mid ;
				else
				    k = mid ;
			}
			if(t == 1)
			    t = 2;
			if(k == 1)
			    k = 2; 
			s1 = b*1.0/k;
			s2 = b*1.0/t;
			if(s1 >= y && s2 >= y){
			    double temp = s1 > s2 ? s2 : s1 ;
				ans = temp;
			}
			else if(s1 >= y)
			    ans = ans > s1 ? s1 : ans;
			else if(s2 >= y)
			    ans = ans > s2 ? s2 : ans;
			printf("%.12lf
",ans);
	} 

	return 0;
}
原文地址:https://www.cnblogs.com/jxgapyw/p/4815422.html