首页 > 代码库 > Aizu 2303 Marathon Match 概率dp
Aizu 2303 Marathon Match 概率dp
题目链接:点击打开链接
题意:
一场马拉松
给定n个运动员,跑道上有m个休息站,马拉松跑道长L
下面n行每行3个参数
表示每个运动员崩溃概率:P 休息时间:E 跑步速度:V。
每个运动员随时会崩溃,崩溃后会坚持到下一个休息站,进入休息他的休息时间。全程匀速运动,可能多次崩溃。
问:
每个运动员成为唯一一个第一名的概率。
思路:
其实可以转换成每个运动员进入下一个休息站的概率是P
每次单独求一个运动员成为第一名的概率。
暴力枚举这个运动员进入休息站的次数。
然后枚举其他的运动员比他慢的概率,相乘得到这个运动员崩溃j次后依然是第一名的概率,相加即是他成为第一名的概率。
#include<bits/stdc++.h> template <class T> inline bool rd(T &ret) { char c; int sgn; if(c=getchar(),c==EOF) return 0; while(c!='-'&&(c<'0'||c>'9')) c=getchar(); sgn=(c=='-')?-1:1; ret=(c=='-')?0:(c-'0'); while(c=getchar(),c>='0'&&c<='9') ret=ret*10+(c-'0'); ret*=sgn; return 1; } template <class T> inline void pt(T x) { if (x <0) { putchar('-'); x = -x; } if(x>9) pt(x/10); putchar(x%10+'0'); } using namespace std; typedef long long ll; const int MAXN = 55; double C[MAXN+1][MAXN+1]; void Initial() { memset(C, 0, sizeof C); for(int i=0; i<=MAXN; ++i) { C[0][i] = 0.0; C[i][0] = 1.0; } for(int i=1; i<=MAXN; ++i) { for(int j=1; j<=MAXN; ++j) C[i][j] = C[i-1][j] + C[i-1][j-1]; } } const int N = 110; int n, m; int l, t[N], v[N]; double p[N]; double Pow(double x, int y){ double ans = 1.0; while(y){ if(y&1)ans *= x; x = x*x; y >>= 1; } return ans; } double work(int x){ double ans = 0.0; for(int i = 0; i <= m; i++) { double pp = C[m][i] * Pow(p[x], i) * Pow(1.0-p[x], m-i); for(int j = 1; j <= n; j++) { if(j == x)continue; double siz = 0; for(int k = m; k >= 0; k--) { if(l*v[j] + i*t[x]*v[j]*v[x] < l*v[x] + k*t[j]*v[x]*v[j]) siz += C[m][k] * Pow(p[j], k) * Pow(1.0-p[j], m-k); else break; } pp *= siz; } ans += pp; } return ans; } void input(){ for(int i = 1; i <= n; i++) { rd(p[i]);rd(t[i]);rd(v[i]); p[i] /= 100.0; } } int main(){ Initial(); while(cin>>n>>m>>l){ input(); for(int i = 1; i <= n; i++) printf("%.10f\n", work(i)); } return 0; } /* 30 0 12 0.5 0 13 */
Marathon Match
Time Limit : 5 sec, Memory Limit : 65536 KBMarathon Match
N people run a marathon. There are M resting places on the way. For each resting place, the i-th runner takes a break with probability Pi percent. When the i-th runner takes a break, he gets rest for Ti time.
The i-th runner runs at constant speed Vi, and the distance of the marathon is L.
You are requested to compute the probability for each runner to win the first place. If a runner arrives at the goal with another person at the same time, they are not considered to win the first place.
Input
A dataset is given in the following format:
N M L
P1 T1 V1
P2 T2 V2
…
PN TN VN
The first line of a dataset contains three integers N (1≤N≤100), M (0≤M≤50) and L(1≤L≤100,000). N is the number of runners. M is the number of resting places. L is the distance of the marathon.
Each of the following N lines contains three integers Pi (0≤Pi≤100), Ti (0≤Ti≤100) and Vi(0≤Vi≤100) describing the i-th runner. Pi is the probability to take a break. Ti is the time of resting. Vi is the speed.
Output
For each runner, you should answer the probability of winning. The i-th line in the output should be the probability that the i-th runner wins the marathon. Each number in the output should not contain an error greater than 10?5.
Sample Input 1
2 2 50 30 50 1 30 50 2
Output for the Sample Input 1
0.28770000 0.71230000
Sample Input 2
2 1 100 100 100 10 0 100 1
Output for the Sample Input 2
0.00000000 1.00000000
Sample Input 3
3 1 100 50 1 1 50 1 1 50 1 1
Output for the Sample Input 3
0.12500000 0.12500000 0.12500000
Sample Input 4
2 2 50 30 0 1 30 50 2
Output for the Sample Input 4
0.51000000 0.49000000
Aizu 2303 Marathon Match 概率dp