Luogu P2473 奖励关 (状压DP, 期望)

https://www.luogu.com.cn/problem/P2473

image

  • 倒推
  • f[i][S] 表示1到i-1关拿的物品集合为S,从i到最后的期望
  • 不知道下一关出现的是哪种物品,所以当前的期望是下一步所有情况的最优决策乘 1/k。
#include<bits/stdc++.h>
using namespace std;
#define IOS ios::sync_with_stdio(false) ,cin.tie(0), cout.tie(0);
//#pragma GCC optimize(3,"Ofast","inline")
#define ll long long
//#define int long long
const int N = 2e5 + 5;
const int M = 1e5 + 5;
const int INF = 0x3f3f3f3f;
const ll LNF = 0x3f3f3f3f3f3f3f3f;
const int mod = 1e9 + 7;
const double PI = acos(-1.0);
int p[16], a[16];
double f[105][1 << 16];
int main () {
 IOS
 int n, k; cin >> n >> k;

 for ( int i = 0; i < k; ++ i ) {
   cin >> a[i]; int x;
   while( cin >> x ) {
     if( !x ) break;
     -- x; p[i] |= ( 1 << x );
   }
 }

 for ( int i = n; i >= 1; -- i) {
   for ( int S = 0; S < 1 << k; ++ S ) {
     for ( int j = 0; j < k; ++ j ) {
       if( (S & p[j]) == p[j] ) {
         f[i][S] += max( f[i + 1][S], f[i + 1][S | (1 << j)] + a[j]);
       } else {
         f[i][S] += f[i + 1][S];
       }
     }
     f[i][S] /= k;
   }
 }
 printf("%.6lf\n", f[1][0]);
 return 0;
}
posted @ 2022-05-17 17:15  qingyanng  阅读(14)  评论(0编辑  收藏  举报