codeforces 698 C. LRU (概率与期望+状压DP)

C. LRU
time limit per test
2 seconds
memory limit per test
256 megabytes
input
standard input
output
standard output

While creating high loaded systems one should pay a special attention to caching. This problem will be about one of the most popular caching algorithms called LRU (Least Recently Used).

Suppose the cache may store no more than k objects. At the beginning of the workflow the cache is empty. When some object is queried we check if it is present in the cache and move it here if it's not. If there are more than k objects in the cache after this, the least recently used one should be removed. In other words, we remove the object that has the smallest time of the last query.

Consider there are n videos being stored on the server, all of the same size. Cache can store no more than k videos and caching algorithm described above is applied. We know that any time a user enters the server he pick the video i with probability pi. The choice of the video is independent to any events before.

The goal of this problem is to count for each of the videos the probability it will be present in the cache after 10100 queries.

Input

The first line of the input contains two integers n and k (1 ≤ k ≤ n ≤ 20) — the number of videos and the size of the cache respectively. Next line contains n real numbers pi (0 ≤ pi ≤ 1), each of them is given with no more than two digits after decimal point.

It's guaranteed that the sum of all pi is equal to 1.

Output

Print n real numbers, the i-th of them should be equal to the probability that the i-th video will be present in the cache after 10100queries. You answer will be considered correct if its absolute or relative error does not exceed 10 - 6.

Namely: let's assume that your answer is a, and the answer of the jury is b. The checker program will consider your answer correct, if .

Examples
input
3 1
0.3 0.2 0.5
output
0.3 0.2 0.5 
input
2 1
0.0 1.0
output
0.0 1.0 
input
3 2
0.3 0.2 0.5
output
0.675 0.4857142857142857 0.8392857142857143 
input
3 3
0.2 0.3 0.5
output
1.0 1.0 1.0 


题目大意:有一个大小为k的缓存区,每次从n种物品中按照一定的概率选取一种物品尝试放进去.同一个物品每一次选取的概率都是相同的.如果这种物品已经放进去过就不再放进去.如果缓存区满了就把放进去的时间离现在最远的物品拿出来.问10^100次后每个物品在缓冲区中的概率.

题解:概率与期望+状压DP

如果是正着考虑,那么我们会出现很多废弃的状态。而且还会出现进去的被弹出来的情况,十分不好想。那么我们倒着考虑,那么最后一次加入的一定在最终的集合中。因为10^100基本上接近无限了,那么最后的集合一定是满的。

也就是一定存在k个不同的物品。

dp[i]表示到达状态i的概率。

dp[i|(1<

#include
#include
#include
#include
#include
#define N 21
using namespace std;
int n,k;
double ans[1<>j)&1) cnt++,now+=p[j];
		if (cnt==k) {
			for (int j=0;j>j)&1) ans[j]+=f[i];
			continue;
		}
		if (cnt>k) continue;
		if (1.0-now==0) continue;
		f[i]/=(1.0-now);
		for (int j=0;j>j)&1)) f[i|(1<




你可能感兴趣的:(动态规划,概率与期望)