首页 > 其他分享 >题解 CF698C【LRU】

题解 CF698C【LRU】

时间:2024-03-30 16:44:31浏览次数:13  
标签:概率 CF698C 队列 题解 sum 物品 LRU varnothing include

题解 CF698C【LRU】

题目描述

有 \(n\) 种物品和大小为 \(k\) 的队列。每次操作,以 \(p_i\) 的概率选择第 \(i\) 种物品放入队尾,如果已经有物品 \(i\) 了就将物品 \(i\) 拿出来扔到队尾。若队列大小 \(\gt k\) ,弹出队首。

求 \(10^{100}\) 次操作后每种物品在队列里的概率。\(1\leq k\leq n\leq 20, \sum_ip_i=1\)。

solution

考虑如何求出物品 \(r\) 的答案。我们在这里用集合 \(S\) 表示队列中在 \(r\) 后面的物品,当 \(r\) 不在队列中时将 \(S\) 记为 \(?\),并始终有 \(r\not\in S\)。因为我们观察到我们很难去维护 \(r\) 前面的物品的顺序和弹出时间,进一步发现这根本没有用,因为我们只关心 \(r\) 的死活,当 \(r\) 后面的元素有 \(k-1\) 个的时候,\(r\) 就死了,与 \(r\) 前面怎么死的没有关系。那么:

  • 当 \(S=?\) 时,以 \(p_r\) 概率转移至 \(\varnothing\),以 \(1-p_r\) 概率转移至 \(?\)。
  • 当 \(S\neq ?\) 时,
    • 以 \(p_r\) 概率转移至 \(\varnothing\)。
    • 以 \(\sum_{i\in S}p_i\) 的概率转移到 \(S\)。
    • 对于 \(j\not \in S\),以 \(p_j\) 的概率转移,若 \(|S|=k-1\) 则转移至 \(?\),否则转移至 \(S\cup \{j\}\)。

如果最终是状态 \(S\) 的概率是可以计算的,那么记为 \(f_S\)。那么有:

  • \(f_?=(1-p_r)f_?+\sum_{|S|=k-1}\sum_{i\not \in S}p_if_S\)。
  • \(f_{\varnothing}=p_r(f_?+\sum_{S}f_S)\)。因为所有状态的概率之和理应 \(=1\),所以 \(f_\varnothing=p_r\)。
  • \(f_{S\neq\varnothing}=\sum_{i\in S}p_if_S+[|S|<k-1]\sum_{j\in S}p_jf_{S\setminus\{j\}}\)。

这样看来,因为答案不仅能表示成 \(1-f_?\) 还能表示为 \(\sum_{|S|<k}f_S\),所以直接根据第三条转移即可。这里可以将\(\sum_{i\in S}p_if_S\) 这一项移动位置使之成为:

\[(1-\sum_{i\in S}p_i)f_{S}=[|S|<k-1]\sum_{j\in S}p_jf_{S\setminus\{j\}},S\neq \varnothing. \]

就有

\[f_{S}=\frac{\sum_{j\in S}p_jf_{S\setminus\{j\}}}{1-\sum_{i\in S}p_i},0<|S|<k-1. \]

这个东西的计算就很轻易了。

code

#include <algorithm>
#include <cstdio>
#include <cstring>
#include <vector>
using namespace std;
#ifdef LOCAL
#define debug(...) fprintf(stderr, ##__VA_ARGS__)
#else
#define debug(...) void(0)
#endif
#define popcount __builtin_popcount
typedef long long LL;
int getbit(int x) { return 1 << x; }
bool conbit(int x, int k) { return getbit(k) & x; }
int lowbit(int x) { return x & -x; }
int n, k;
double p[1 << 20], f[1 << 20];
double solve(int r) {
  if (p[1 << r] < 1e-5) return 0;
  memset(f, 0, sizeof f);
  f[0] = p[1 << r];
  // f[0]=p[R]
  // f[S] 表示 r 前面的元素是 S,不能包括 r
  // f[S]=>f[S] (p[S])
  // f[S]=>f[S^J] (p[J],j not in S,j!=r)
  // f[S]=>f[0] (p[r])
  for (int S = 0; S < 1 << n; S++) {
    if (conbit(S, r)) continue;
    f[S] /= 1 - p[S];
    for (int j = 0; j < n; j++)
      if (!conbit(S, j) && j != r) {
        int J = 1 << j;
        f[S ^ J] += f[S] * p[J];
      }
  }
  double ans = 0;
  for (int i = 0; i < 1 << n; i++)
    if (popcount(i) < k) ans += f[i];
  return ans;
}
int main() {
  //    #ifdef LOCAL
  //            freopen("input.in","r",stdin);
  //    #endif
  scanf("%d%d", &n, &k);
  for (int i = 0; i < n; i++) scanf("%lf", &p[1 << i]);
  for (int i = 1; i < 1 << n; i++) p[i] = p[i ^ lowbit(i)] + p[lowbit(i)];
  for (int i = 0; i < n; i++) printf("%.10lf%c", solve(i), " \n"[i == n - 1]);
  return 0;
}

标签:概率,CF698C,队列,题解,sum,物品,LRU,varnothing,include
From: https://www.cnblogs.com/caijianhong/p/18105705/solution-CF698C

相关文章

  • upload-labs简单题解
    upload-labs详解1-19关通关全解(最全最详细一看就会)-CSDN博客Upload-labs1-21关靶场通关笔记(含代码审计)_upload-labs21关-CSDN博客搭建upload-labs环境参考文章渗透测试——upload-labs环境部署_upload-loadsphpstudy-CSDN博客文件上传浅谈-CSDN博客 Pass-01考点:J......
  • 题解 ARC175C【Jumping Through Intervals】
    先不考虑构造字典序最小的方案,只考虑求出最小的\(\sum\limits_{i=1}^{N-1}|A_{i+1}-A_i|\)。设定义域为\([L_i,R_i]\)的函数\(F_i(x)\)表示考虑后缀\([i,N]\),令\(A_i=x\)时上式最小的值。初值为\(F_N(x)=0,(x\in[L_N,R_N])\)。显然有转移方程:\[F_i(x)=\min\limits_{y......
  • 题解 CF70E【Information Reform】
    题解CF70E【InformationReform】题目描述\(n\)个点的树,边权为\(1\)。可以花费常数\(k\),在一个点上建基站。每个点\(i\)需要找到离他最近的基站\(a_i\),花费\(d[dis(i,a_i)]\)。一种方案的总花费是建基站的花费加上每个点的花费之和。最小化总花费。输出方案\(a_i\)。......
  • ICPC2023 陕西邀请赛 题解
    G-PermutationQuestion找到一个排列\(p\),使得\(\prod_{i=1}^nlcm(p_i,p_{(imodn)+1})\)最大Solution考虑到\(x\)和\(x-1\)必然是互质的所以顺序排列即可Code#include<bits/stdc++.h>usingnamespacestd;intmain(){intn;cin>>n;for(inti......
  • 快递员的烦恼【华为OD机试JAVA&Python&C++&JS题解】
    一.题目-快递员的烦恼快递公司每日早晨,给每位快递员推送需要送到客户手中的快递以及路线信息,快递员自己又查找了一些客户与客户之间的路线距离信息,请你依据这些信息,给快递员设计一条最短路径,告诉他最短路径的距离。注意:不限制快递包裹送到客户手中的顺序,但必须保证都送......
  • 园区参观路径【华为OD机试JAVA&Python&C++&JS题解】
    一.题目-园区参观路径园区某部门举办了FamilyDay,邀请员工及其家属参加;将公司园区视为一个矩形,起始园区设置在左上角,终点园区设置在右下角;家属参观园区时,只能向右和向下园区前进;求从起始园区到终点园区会有多少条不同的参观路径;输入描述:第一行为园区长和宽;后面每一行表示......
  • [题解]P1439 【模板】最长公共子序列
    P1439【模板】最长公共子序列题意简述给出\(1,2,…,n\)的两个排列\(P_1\)和\(P_2\),求它们的最长公共子序列。范围限制:\(n\le10^5\)。样例53214512345输出:3。思路简述这道题看似是最长公共子序列,但是发现如果用\(O(n^2)\)的复杂度实现\(LCS\)就会时......
  • 2024年03月CCF-GESP编程能力等级认证C++编程八级真题解析
    本文收录于专栏《C++等级认证CCF-GESP真题解析》,专栏总目录:点这里。订阅后可阅读专栏内所有文章。一、单选题(每题2分,共30分)第1题为丰富食堂菜谱,炒菜部进行头脑风暴。肉类有鸡肉、牛肉、羊肉、猪肉4种,切法有肉排、肉块、肉末3种,配菜有圆白菜、油菜、豆腐3种,辣度有......
  • 2024年03月CCF-GESP编程能力等级认证C++编程七级真题解析
    本文收录于专栏《C++等级认证CCF-GESP真题解析》,专栏总目录:点这里。订阅后可阅读专栏内所有文章。一、单选题(每题2分,共30分)第1题下列关于排序的说法,正确的是()。A.冒泡排序是最快的排序算法之一。B.快速排序通常是不稳定的。C.最差情况,N个元素做归并排序......
  • LRU
    LRUhttps://leetcode.cn/problems/lru-cache/description/?envType=study-plan-v2&envId=top-100-likedclassLRUCache{HashMap<Integer,DLinkedNode>map;intdLinkSize;intcapacity;DLinkedNodehead;DLinkedNodetail;class......