1. 程式人生 > >HDU 5984 Pocky 數學期望

HDU 5984 Pocky 數學期望

Pocky

Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others) Total Submission(s): 2004    Accepted Submission(s): 1065

Problem Description

Let’s talking about something of eating a pocky. Here is a Decorer Pocky, with colorful decorative stripes in the coating, of length L. While the length of remaining pocky is longer than d, we perform the following procedure. We break the pocky at any point on it in an equal possibility and this will divide the remaining pocky into two parts. Take the left part and eat it. When it is not longer than d, we do not repeat this procedure. Now we want to know the expected number of times we should repeat the procedure above. Round it to 6 decimal places behind the decimal point.

Input

The first line of input contains an integer N which is the number of test cases. Each of the N lines contains two float-numbers L and d respectively with at most 5 decimal places behind the decimal point where 1 ≤ d, L ≤ 150.

Output

For each test case, output the expected number of times rounded to 6 decimal places behind the decimal point in a line.

Sample Input

6 
1.0 1.0 
2.0 1.0 
4.0 1.0 
8.0 1.0 
16.0 1.0 
7.00 3.00

Sample Output

0.000000 
1.693147 
2.386294 
3.079442 
3.772589 
1.847298

Source

題解

題意相對比較容易理解 對於一根長度為 L 的木棍,每次等概率的取一個點將其分成兩半,然後吃掉左邊一半,直到剩下的長度小於 d,計算需要吃(分割)次數的數學期望

顯然,如果 L/d 相同,則結果必定相同 根據 ln2 = 0.693147 可以推測出結果應該是 ln(L/d) + 1 再單獨考慮不需要分割的情況( d>=L

 ),結果是0次

證明

定義 f(x) 為長度為 x 時,的數學期望 如圖,對於 f(x) 若 x<=d 這時已經滿足條件,有 f(x)=0 而對於 x>d 其結果應該是從上面任選一點後求其右半部份的數學期望再加上本次分割的 1

用 φ 表示從長度為 x 的線段上取到一個點的概率,有     也即   

也即

其中,特別要注意的是

因此可以得知 f(x) 不是一個連續函式 但是我們迭代運算的部分都是 x > d 部分

原文地址

#include<stdio.h>
#include<string.h>
#include<queue>
#include<cstdio>
#include<string>
#include<math.h>
#include<algorithm>
#define LL long long
#define PI atan(1.0)*4
#define DD double
#define mod 100
#define dian 1.000000011
#define INF 0x3f3f3f3f
#define eps 1e-6
using namespace std;
const int maxn=6e3;

int main()
{
    int T;
    scanf("%d",&T);
    while(T--){
        double x,d;
        scanf("%lf%lf",&x,&d);
        if(x-d<=eps)
            printf("0.000000\n");
        else
            printf("%.6lf\n",log(x/d)+1);
    }
    return 0;
}