【XSY2332】Randomized Binary Search Tree 概率DP FFT
题目描述
\(\forall 0\leq i<n\),求有多少棵\(n\)个点,权值和优先级完全随机的treap的树高为\(i\)。
\(n\leq 30000\)
题解
设\(f_{i,j}\)为\(j\)个点的树,树高不超过为\(i\)的概率
\]
枚举一个点左子树大小\(k-1\),那么右子树大小为\(j-k\)。且这个点的优先级为这\(j\)个点最小的概率是\(\frac{1}{j}\)。
这个东西是个卷积,可以用FFT加速。
其实期望树高是\(O(\log n)\)的。实际上只有前面一部分的答案不为\(0\)。所以我们只用计算树高\(\leq 100\)的答案。
时间复杂度:\(O(n\log^2n)\)
代码
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cstdlib>
#include<ctime>
#include<utility>
#include<cmath>
using namespace std;
typedef long long ll;
typedef unsigned long long ull;
typedef pair<int,int> pii;
double pi=acos(-1);
struct cp
{
double x,y;
cp(double a=0,double b=0)
{
x=a;
y=b;
}
};
cp operator +(cp a,cp b)
{
return cp(a.x+b.x,a.y+b.y);
}
cp operator -(cp a,cp b)
{
return cp(a.x-b.x,a.y-b.y);
}
cp operator *(cp a,cp b)
{
return cp(a.x*b.x-a.y*b.y,a.x*b.y+a.y*b.x);
}
cp operator /(cp a,double b)
{
return cp(a.x/b,a.y/b);
}
namespace fft
{
cp w1[100010];
cp w2[100010];
int rev[100010];
int n;
void init(int m)
{
n=1;
while(n<=m)
n<<=1;
int i;
for(i=2;i<=n;i<<=1)
{
w1[i]=cp(cos(2*pi/i),sin(2*pi/i));
w2[i]=cp(cos(2*pi/i),-sin(2*pi/i));
}
rev[0]=0;
for(i=1;i<n;i++)
rev[i]=(rev[i>>1]>>1)|(i&1?n>>1:0);
}
void fft(cp *a,int t)
{
int i,j,k;
cp u,v,w,wn;
for(i=0;i<n;i++)
if(rev[i]<i)
swap(a[i],a[rev[i]]);
for(i=2;i<=n;i<<=1)
{
wn=(~t?w1[i]:w2[i]);
for(j=0;j<n;j+=i)
{
w=1;
for(k=j;k<j+i/2;k++)
{
u=a[k];
v=a[k+i/2]*w;
a[k]=u+v;
a[k+i/2]=u-v;
w=w*wn;
}
}
}
if(t==-1)
for(i=0;i<n;i++)
a[i]=a[i]/n;
}
}
cp a[100010];
double f[110][30010];
double ans[30010];
int main()
{
freopen("b.in","r",stdin);
freopen("b.out","w",stdout);
int n;
scanf("%d",&n);
int m=100;
int i,j;
fft::init(2*n);
a[0]=a[1]=1;
double last;
for(i=0;i<n;i++)
ans[i]=0;
last=ans[0]=a[n].x;
for(i=1;i<=m;i++)
{
fft::fft(a,1);
for(j=0;j<fft::n;j++)
a[j]=a[j]*a[j];
fft::fft(a,-1);
for(j=fft::n-1;j>=1;j--)
a[j]=a[j-1];
a[0]=a[1]=1;
for(j=2;j<=n;j++)
a[j]=a[j]/j;
for(j=n+1;j<fft::n;j++)
a[j]=0;
ans[i]=a[n].x-last;
last=a[n].x;
}
// for(i=0;i<=m;i++)
// f[i][1]=f[i][0]=1;
// for(i=1;i<=m;i++)
// for(j=2;j<=n;j++)
// for(k=1;k<=j;k++)
// f[i][j]+=f[i-1][k-1]*f[i-1][j-k]/j;
// for(i=0;i<=m;i++)
// {
// ans[i]=f[i][n];
// if(i>=1)
// ans[i]-=f[i-1][n];
// }
for(i=0;i<=n-1;i++)
printf("%.10lf\n",ans[i]);
return 0;
}
【XSY2332】Randomized Binary Search Tree 概率DP FFT的更多相关文章
- 【xsy2332】Randomized Binary Search Tree DP+FFT
题目大意:给你一个$[0,1]$之间等概率随机序列,你需要把这个序列插入到一棵$treap$中,问这棵$treap$的期望深度,请对于$[1,n]$中的每个深度分别输出它的概率(实数,保留五位小数). ...
- 【未知来源】Randomized Binary Search Tree
题意 求 \(n\) 个点的 Treap 深度为 \(h=0,1,2,\cdots,n\) 的概率. Treap 是一个随机二叉树,每个节点有权值和优先级,权值和优先级都是 \([0,1]\) 中的随 ...
- uva 10304 - Optimal Binary Search Tree 区间dp
题目链接 给n个数, 这n个数的值是从小到大的, 给出个n个数的出现次数. 然后用他们组成一个bst.访问每一个数的代价是这个点的深度*这个点访问的次数. 问你代价最小值是多少. 区间dp的时候, 如 ...
- 笔试算法题(58):二分查找树性能分析(Binary Search Tree Performance Analysis)
议题:二分查找树性能分析(Binary Search Tree Performance Analysis) 分析: 二叉搜索树(Binary Search Tree,BST)是一颗典型的二叉树,同时任 ...
- [数据结构]——二叉树(Binary Tree)、二叉搜索树(Binary Search Tree)及其衍生算法
二叉树(Binary Tree)是最简单的树形数据结构,然而却十分精妙.其衍生出各种算法,以致于占据了数据结构的半壁江山.STL中大名顶顶的关联容器--集合(set).映射(map)便是使用二叉树实现 ...
- Leetcode 笔记 99 - Recover Binary Search Tree
题目链接:Recover Binary Search Tree | LeetCode OJ Two elements of a binary search tree (BST) are swapped ...
- Leetcode 笔记 98 - Validate Binary Search Tree
题目链接:Validate Binary Search Tree | LeetCode OJ Given a binary tree, determine if it is a valid binar ...
- Leetcode: Convert sorted list to binary search tree (No. 109)
Sept. 22, 2015 学一道算法题, 经常回顾一下. 第二次重温, 决定增加一些图片, 帮助自己记忆. 在网上找他人的资料, 不如自己动手. 把从底向上树的算法搞通俗一些. 先做一个例子: 9 ...
- [LeetCode] Closest Binary Search Tree Value II 最近的二分搜索树的值之二
Given a non-empty binary search tree and a target value, find k values in the BST that are closest t ...
随机推荐
- 牛客---java练习
一. 1. abstract可以修饰方法和类,不能修饰属性.抽象方法没有方法体,即没有大括号{}.抽象类中的成员属性都是public static final类型的:成员方法都是public abst ...
- 求n!中含有某个因子个数的方法
链接 [https://www.cnblogs.com/dolphin0520/archive/2011/04/11/2012891.html]
- p9半幺群
如何不理解划红线的地方?第二个划红线地方,请举一个例子 1.0不是幺元 2.f(1)=2, f(2)=1, f(3)=3, g(1)=2, g(2)=3, g(3)=1 fg不等于gf
- MySql concat与字符转义
mysql函数之四:concat() mysql 多个字段拼接 - duanxz - 博客园https://www.cnblogs.com/duanxz/p/5098875.html mysql 多个 ...
- virtualization - Ubuntu Budgie screen distortion in Hyper-V - Ask Ubuntu
virtualization - Ubuntu Budgie screen distortion in Hyper-V - Ask Ubuntuhttps://askubuntu.com/questi ...
- [转帖]Stack的三种含义
Stack的三种含义 http://www.ruanyifeng.com/blog/2013/11/stack.html 学习编程的时候,经常会看到stack这个词,它的中文名字叫做"栈&q ...
- spring IOC源码分析(ApplicationContext)
在上一篇文章中,我们以BeanFactory这条主线进行IOC的源码解析的,这里,将以ApplicationContext这条线进行分析.先看使用方法: @Test public void testA ...
- CSS实现元素水平垂直居中
我们知道,实现元素的水平居中比较简单,在设置了宽度后,设置左右margin为auto就可以. 但是如何设置元素垂直居中呢? 当然,对于单行的文字,可以通过设置line-height来解决, 可以对于一 ...
- Leetcode SingleNumber I & II & III 136/137/260
SingleNumber I: 题目链接:https://leetcode-cn.com/problems/single-number/ 题意: 给定一个非空整数数组,除了某个元素只出现一次以外,其余 ...
- 神经网络-SGD-2
接上节: 3.梯度(gradient): def numerical_gradient(f,x): h=1e-5 grad=np.zeros_like(x) for index_x in range( ...