【LOJ2513】「BJOI2018」治疗之雨
题意
你现在有 \(m+1\) 个数:第一个为 \(p\) ,最小值为 \(0\) ,最大值为 \(n\) ;剩下 \(m\) 个都是无穷,没有最小值或最大值。你可以进行任意多轮操作,每轮操作如下:
在不为最大值的数中等概率随机选择一个(如果没有则不操作),把它加一;
进行 \(k\) 次这个步骤:在不为最小值的数中等概率随机选择一个(如果没有则不操作),把它减一。
现在问期望进行多少轮操作以后第一个数会变为最小值 \(0\)。
\(1 \leq p \leq n \leq 1500\) ,\(0 \leq m, k \leq 10^9\) 。
Solution
显然我们只用考虑第一个数的变化。
设 \(P_x\) 表示一次操作 \(-x\) 概率,即 \(k\) 次中选出 \(x\) 次,剩余 \(k-x\) 次分配到其他 \(m\) 个数。
\]
设 \(Q_{x,y}\) 表示一次操作从 \(x\) 变到 \(y\) 的概率,不难推出
\left\{
\begin{array}{lr}
0 & x=n 且 y=n+1 &\\
P_{x-y} & x=n\\
\frac{1}{m+1}P_0 & y=x+1\\
\frac{m}{m+1}P_{x-y}+\frac{1}{m+1}P_{x-y+1} & \text{otherwise}
\end{array}
\right.
\end{equation}
\]
设 \(f(i)\) 表示从 \(i\) 变到 \(0\) 的期望操作数。
& f(i)=1+\sum_{j=1}^{i+1} Q_{i,j}f(j) & (1\le i<n) \\
& f(n)=1+\sum_{j=1}^nQ_{n,j}f(j)
\end{align}
\]
我们可以 \(n^2\) 消元上述式子。将 \((1)\) 变形可得
f(i+1)=\frac{f(i)-\sum_{j=1}^iQ_{i,j}f(j)-1}{Q_{i,i+1}}
\end{align}
\]
可以利用 \((3),(4)\) 得到 \(f(n)\) 关于 \(f(1)\) 的两个方程,解出 \(f(1)\) 后带入即可。
Code
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
const int Mod=1e9+7,N=1505;
inline int mul(int x, int y) { return 1ll*x*y%Mod; }
inline int po(int x, int y)
{
int r=1;
while(y)
{
if(y&1) r=mul(r,x);
x=mul(x,x), y>>=1;
}
return r;
}
int f[N],x[N],y[N],fac[N],inv[N],n,p,m,k,iv;
inline int calcp(int x, int y)
{
if(x==n&&y==n+1) return 0;
if(x==n) return f[x-y];
if(y==x+1) return mul(iv,f[0]);
return (mul(mul(m,iv),f[x-y])+mul(f[x-y+1],iv))%Mod;
}
int main()
{
int T; scanf("%d",&T);
fac[0]=inv[0]=1;
for(int i=1;i<=1500;++i) fac[i]=mul(i,fac[i-1]);
inv[1500]=po(fac[1500],Mod-2);
for(int i=1499;i;--i) inv[i]=mul(inv[i+1],i+1);
while(T--)
{
scanf("%d%d%d%d",&n,&p,&m,&k);
if(!k||(!m&&k==1))
{
puts("-1");
continue;
}
if(!m)
{
int ans=0;
while(p>0)
{
if(p<n) ++p;
p-=k,++ans;
}
printf("%d\n",ans);
continue;
}
int inv0=po(m,Mod-2),inv1=po(po(m+1,k),Mod-2);
iv=po(m+1,Mod-2);
for(int i=0,j=1,g=po(m,k),l=min(n,k);i<=l;++i)
{
f[i]=mul(mul(mul(j,inv[i]),g),inv1);
j=mul(j,k-i),g=mul(g,inv0);
}
x[1]=1,y[1]=0;
for(int i=2;i<=n;++i)
{
x[i]=x[i-1],y[i]=(Mod+y[i-1]-1)%Mod;
for(int j=1;j<i;++j)
{
int tmp=calcp(i-1,j);
x[i]=(x[i]+Mod-mul(x[j],tmp))%Mod;
y[i]=(y[i]+Mod-mul(y[j],tmp))%Mod;
}
int tmp=po(calcp(i-1,i),Mod-2);
x[i]=mul(x[i],tmp),y[i]=mul(y[i],tmp);
}
int nx=0,ny=1;
for(int i=1;i<=n;++i)
{
int tmp=calcp(n,i);
nx=(nx+mul(x[i],tmp))%Mod;
ny=(ny+mul(y[i],tmp))%Mod;
}
int tmp=mul((ny-y[n]+Mod)%Mod,po((x[n]-nx+Mod)%Mod,Mod-2));
printf("%d\n",(mul(tmp,x[p])+y[p])%Mod);
memset(f,0,sizeof(int)*(min(n,k)+1));
}
}
【LOJ2513】「BJOI2018」治疗之雨的更多相关文章
- 【LOJ】#2513. 「BJOI2018」治疗之雨
题解 具体就是列一个未知数方程\(dp[i]\)表示有\(i\)滴血的时候期望多少轮 \(dp[i] = 1 + \sum_{j = 1}^{i + 1} a_{i,j}dp[j]\) \(dp[n] ...
- 「BJOI2018」治疗之雨
传送门 Description 有\(m+1\)个数,第一个数为\(p\),每轮:选一个数\(+1\),再依次选\(k\)个数\(-1\) 要求如果第一个数\(=N\),不能选它\(+1\),如果第一 ...
- 「BJOI2018」链上二次求和
「BJOI2018」链上二次求和 https://loj.ac/problem/2512 我说今天上午写博客吧.怕自己写一上午,就决定先写道题. 然后我就调了一上午线段树. 花了2h找到lazy标记没 ...
- 「BJOI2018」求和
「BJOI2018」求和 传送门 观察到 \(k\) 很小而且模数不会变,所以我们直接预处理 \(k\) 取所有值时树上前缀答案,查询的时候差分一下即可. 参考代码: #include <alg ...
- 【LOJ】#2511. 「BJOI2018」双人猜数游戏
题解 设\(f[p][a][b]\)表示询问了\(p\)次,答案是\(a,b\)是否会被猜出来 然后判断如果\(p = 1\) 第一个问的\(Alice\),那么\([s,\sqrt{nm}]\)约数 ...
- 【LOJ】#2493. 「BJOI2018」染色
题面 题解 推结论大题--然而我推不出什么结论 奇环显然是NO 如果一个联通块里有两个分离的环,也是NO 如果一个联通块里,点数为n,边数为m m <= n的时候,是YES m >= n ...
- 【LOJ】#2492. 「BJOI2018」二进制
题解 每次开这样的数据结构题感想都大概是如下两点 1.为什么别人代码长度都是我的1/2???? 2.为什么我运行时间都是他们的两倍???? 简单分析一下,我们关注一个区间是否合法只关注这个区间有多少个 ...
- 【LOJ】#2512. 「BJOI2018」链上二次求和
题面 题解 转化一下可以变成所有小于等于r的减去小于等于l - 1的 然后我们求小于等于x的 显然是 \(\sum_{i = 1}^{n} \sum_{j = 1}^{min(i,x)} sum[i] ...
- 【LOJ】#2491. 「BJOI2018」求和
题解 对于50个k都维护一个\(i^k\)前缀和即可 查询的时候就是查询一段连续的区间和,再加上根节点的 代码 #include <bits/stdc++.h> #define fi fi ...
随机推荐
- UNL/EVE关联putty和wireshark
这里默认UNL已经安装完毕,然后启动虚拟机启动UNL. 在浏览器输入http://192.168.1.199/ 进入UNL.然后简单的搭建一个拓扑: 这里只讲R1和ASA开启,先来配置Telnet功能 ...
- 使用vASA842配置ASDM645
准备:使用VMware打开vASA842.ova文件,将第一个网络适配器桥接到一个vmnet接口,我这里是vmnet3,网段是10.0.0.0/24,网关是10.0.0.1/24 1.打开vASA84 ...
- 802.1X高级配置
部署VLAN和ACLCisco Catalyst交换机(认证方)和Cisco ACS(认证服务器)具备动态分配VLAN或者ACL的能力.Cisco ACS可以将某个用户分配给指定的VLAN,或应用AC ...
- 洛谷P1086花生采摘(简单模拟)
题目描述 鲁宾逊先生有一只宠物猴,名叫多多.这天,他们两个正沿着乡间小路散步,突然发现路边的告示牌上贴着一张小小的纸条:“欢迎免费品尝我种的花生!――熊字”. 鲁宾逊先生和多多都很开心,因为花生正是他 ...
- Java27个基数点
1.JAVA中的几种基本数据类型是什么,各自占用多少字节. 2.String类能被继承吗,为什么 不能.在Java中,只要是被定义为final的类,也可以说是被final修饰的类,就是不能被继承的. ...
- MySQL - 设置UTF-8编码
1. 在Windows上,安装时请选择UTF-8编码,以便正确地处理中文. 在Mac或Linux上,需要编辑MySQL的配置文件,把数据库默认的编码全部改为UTF-8.MySQL的配置文件默认存放在/ ...
- 07 DTFT
DTFT 连续时间傅里叶变换(CTFT) 连续时间傅里叶变换的定义为: \[ X(j\Omega)=\int_{-\infty}^{\infty}x_a(t)e^{-j\Omega t}dt \] 其 ...
- Weka算法算法翻译(部分)
目录 Weka算法翻译(部分) 1. 属性选择算法(select attributes) 1.1 属性评估方法 1.2 搜索方法 2. 分类算法 2.1 贝叶斯算法 2.2 Functions 2.3 ...
- 03.使用私有构造方法或枚类实现 Singleton 属性
前言 <Effective Java>中文第三版,是一本关于Java基础的书,这本书不止一次有人推荐我看.其中包括我很喜欢的博客园博主五月的仓颉,他曾在自己的博文<给Java程序猿们 ...
- Unity初步 基本拼图实现
using System.Collections; using System.Collections.Generic; using UnityEngine; using UnityEngine.UI; ...