【题解 P4550】 收集邮票

收集邮票

题目描述

\(n\) 种不同的邮票,皮皮想收集所有种类的邮票。唯一的收集方法是到同学凡凡那里购买,每次只能买一张,并且买到的邮票究竟是 \(n\) 种邮票中的哪一种是等概率的,概率均为 \(1/n\)。但是由于凡凡也很喜欢邮票,所以皮皮购买第 \(k\) 次邮票需要支付 \(k\) 元钱。

现在皮皮手中没有邮票,皮皮想知道自己得到所有种类的邮票需要花费的钱数目的期望。

输入格式

一行,一个数字 \(N\)\(N \le 10000\))。

输出格式

输出要付出多少钱,保留二位小数。

样例 1

样例输入 1

3

样例输出 1

21.25

算法过程

一看就是一道期望 \(DP\)
定义 \(f_i\) 为已经买 \(i\) 种邮票的还需要次数,\(g_i\) 为已经买 \(i\) 种邮票的还需要花费。
显然,\(f_n=0\)
很明显,\(f_i\)\(\frac{i}{n}\) 的概率买到之前的,即为 \(\frac{i}{n}\times f_i\) ,有 \(\frac{n-i}{n}\) 买到新的,即为 \(\frac{n-i}{n} \times f_{i+1}\)
所以 \(f_i=\frac{i}{n}\times f_i+\frac{n-i}{n} \times f_{i+1}+1\)
即为 $ f_i=f_{i+1}+\frac{n}{n-i}$ 。
\(g_i\) 同理,若是之前的,即为已有的花费加上这一次的花费,分别是 \(g_i\)\(f_i+1\) ,就是 \(\frac{i}{n}\times (g_i+f_i+1)\) ,买到新的同上。
所以,\(g_i=\frac{i}{n}\times (g_i+f_i+1)+\frac{n-i}{n}\times (g_{i+1}+f_{i+1}+1)\)
化简,\(g_i=\frac{i}{n-i} \times f_i+g_{i+1}+f_{i+1}+\frac{n}{n-i}\)

Code

#include<bits/stdc++.h>
using namespace std;
long long n,a[1000005];
double f[1000005],l[1000005];
int main()
{
	scanf("%lld",&n);
	for(int i=n-1;i>=0;i--)
	{
		f[i]=f[i+1]+(1.0*n)/(1.0*(n-i));
		l[i]=(1.0*i)/(1.0*(n-i))*(f[i]+1)+l[i+1]+f[i+1]+1;
	}
	printf("%.2lf",l[0]);








  return 0;
}
posted @ 2023-10-06 15:21  dijah  阅读(17)  评论(0编辑  收藏  举报