【组合数学:第一类斯特林数】【HDU3625】Examining the Rooms
Examining the Rooms
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 1138 Accepted Submission(s): 686
one key in each room, and all the possible distributions are of equal possibility. For example, if N = 3, there are 6 possible distributions, the possibility of each is 1/6. For convenience, we number the rooms from 1 to N, and the key for Room 1 is numbered
Key 1, the key for Room 2 is Key 2, etc.
To examine all the rooms, you have to destroy some doors by force. But you don’t want to destroy too many, so you take the following strategy: At first, you have no keys in hand, so you randomly destroy a locked door, get into the room, examine it and fetch
the key in it. Then maybe you can open another room with the new key, examine it and get the second key. Repeat this until you can’t open any new rooms. If there are still rooms un-examined, you have to randomly pick another unopened door to destroy by force,
then repeat the procedure above, until all the rooms are examined.
Now you are only allowed to destroy at most K doors by force. What’s more, there lives a Very Important Person in Room 1. You are not allowed to destroy the doors of Room 1, that is, the only way to examine Room 1 is opening it with the corresponding key. You
want to know what is the possibility of that you can examine all the rooms finally.
3
3 1
3 2
4 2
0.3333
0.6667
0.6250HintSample Explanation When N = 3, there are 6 possible distributions of keys: Room 1 Room 2 Room 3 Destroy Times
#1 Key 1 Key 2 Key 3 Impossible
#2 Key 1 Key 3 Key 2 Impossible
#3 Key 2 Key 1 Key 3 Two
#4 Key 3 Key 2 Key 1 Two
#5 Key 2 Key 3 Key 1 One
#6 Key 3 Key 1 Key 2 One In the first two distributions, because Key 1 is locked in Room 1 itself and you can’t destroy Room 1, it is impossible to open Room 1.
In the third and forth distributions, you have to destroy Room 2 and 3 both. In the last two distributions, you only need to destroy one of Room 2 or Room
递推关系的说明:
考虑第p个物品,p可以单独构成一个非空循环排列,这样前p-1种物品构成k-1个非空循环排列,方法数为s(p-1,k-1);
也可以前p-1种物品构成k个非空循环排列,而第p个物品插入第i个物品的左边,这有(p-1)*s(p-1,k)种方法。
边界条件 s(x,0)=0;s(x,x)=1;
#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
const int maxn=20;
long long f[25],stir[25][25];
int solve()
{
int i,j;
f[0]=1;
for(i=1;i<=maxn;i++)
f[i]=i*f[i-1];
//因为N有N!种排列顺序,这作为总数
//计算概率
for(i=1;i<=maxn;i++)
stir[i][0]=0;
stir[1][1]=1;
for(i=1;i<=maxn;i++)
for(j=1;j<=i;j++)
{
if(i==j)
stir[i][j]=1;
else
stir[i][j]=stir[i-1][j-1]+(i-1)*stir[i-1][j];
}
for(i=1;i<=maxn;i++)
for(j=1;j<=maxn;j++)
if(stir[i][j]<0)
stir[i][j]=-stir[i][j];
return 0;
}
int main()
{
int cas,n,i,k;
long long sum;
solve();
scanf("%d",&cas);
while(cas--)
{
scanf("%d %d",&n,&k);
sum=0;
for(i=1;i<=k;i++)
sum+=stir[n][i]-stir[n-1][i-1];
printf("%.4lf\n",1.0*sum/f[n]);
//因为写成printf("%.4lf\n",(double)sum/f[n]);
//run time error! 下次一定记好了!
}
return 0;
}
接下来是我的方法!
#include <cstdio>
#include <cstdlib>
#include <cmath>
#include <cstring>
#include <ctime>
#include <algorithm>
#include <iostream>
#include <sstream>
#include <string>
#define oo 0x13131313
using namespace std;
long long H[21];
long long F[21][21];
long long T[21];
long long C[21][21];
void CLT(int n,int len)
{
long long tot=n;
long long k=1;
for(int i=1;i<=len;i++)
{
if(T[i]==1)
{
k*=C[tot-1][1];
tot-=T[i];
}
else
{
k*=(C[tot][T[i]]*H[T[i]-1]);
tot-=T[i];
}
}
tot=1;
T[len+1]=0;
for(int i=2;i<=len+1;i++)
{
if(T[i]==T[i-1])
{
tot++;
}
else
{
k=k/H[tot];
tot=1;
}
}
F[n][len]+=k;
}
int getxulie(int n,long long tot,int prev,int len,int deep)
{
T[deep]=prev;
tot+=prev;
if(deep==len)
if(tot==n)
{
CLT(n,len);
return 1;
}
else
return 0;
for(int i=prev;i<=n-len+1;i++)
getxulie(n,tot,i,len,deep+1);
return 0;
}
void YCLYCL()
{
H[0]=1;
for(int i=1;i<=20;i++)
{
H[i]=H[i-1]*i;
}
for(int i=1;i<=20;i++)
C[i][0]=1;
C[1][1]=1;
for(int i=2;i<=20;i++)
for(int j=1;j<=i;j++)
{
C[i][j]=C[i-1][j-1]+C[i-1][j];
}
}
void YCL()
{ YCLYCL();
for(int i=2;i<=20;i++)
for(int j=1;j<=i;j++)
{
for(int k=1;k<=i-j+1;k++)
{
memset(T,0,sizeof(T));
getxulie(i,0,k,j,1);
}
}
for(int i=2;i<=20;i++)
for(int j=1;j<=i;j++)
{
F[i][j]+=F[i][j-1];
}
}
void inin()
{
freopen("a.in","r",stdin);
freopen("a.out","w",stdout);
}
int main()
{
//inin();
YCL();
int K;
cin>>K;
int a;int b;
while(K--)
{
cin>>a>>b;
printf("%.4lf\n",((double)F[a][b]/(double)H[a]));
}
}
【组合数学:第一类斯特林数】【HDU3625】Examining the Rooms的更多相关文章
- [HDU 3625]Examining the Rooms (第一类斯特林数)
[HDU 3625]Examining the Rooms (第一类斯特林数) 题面 有n个房间,每个房间有一个钥匙,钥匙等概率的出现在n个房间内,每个房间中只会出现且仅出现一个钥匙.你能炸开门k次, ...
- hdu 3625 Examining the Rooms —— 第一类斯特林数
题目:http://acm.hdu.edu.cn/showproblem.php?pid=3625 学习斯特林数:https://blog.csdn.net/qq_33229466/article/d ...
- HDU3625(SummerTrainingDay05-N 第一类斯特林数)
Examining the Rooms Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Othe ...
- 【Luogu4609】建筑师(第一类斯特林数,组合数学)
[Luogu4609]建筑师(组合数学) 题面 洛谷 题解 首先发现整个数组一定被最高值切成左右两半,因此除去最高值之后在左右分开考虑. 考虑一个暴力\(dp\) ,设\(f[i][j]\)表示用了\ ...
- HDU 4372 Count the Buildings——第一类斯特林数
题目大意:n幢楼,从左边能看见f幢楼,右边能看见b幢楼 楼高是1~n的排列. 问楼的可能情况 把握看到楼的本质! 最高的一定能看见! 计数问题要向组合数学或者dp靠拢.但是这个题询问又很多,难以dp ...
- 【HDU 4372】 Count the Buildings (第一类斯特林数)
Count the Buildings Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/65536 K (Java/Othe ...
- 如何快速求解第一类斯特林数--nlog^2n + nlogn
目录 参考资料 前言 暴力 nlog^2n的做法 nlogn的做法 代码 参考资料 百度百科 斯特林数 学习笔记-by zhouzhendong 前言 首先是因为这道题,才去研究了这个玩意:[2019 ...
- 【2019雅礼集训】【CF 960G】【第一类斯特林数】【NTT&多项式】permutation
目录 题意 输入格式 输出格式 思路 代码 题意 找有多少个长度为n的排列,使得从左往右数,有a个元素比之前的所有数字都大,从右往左数,有b个元素比之后的所有数字都大. n<=2*10^5,a, ...
- CF960G Bandit Blues 第一类斯特林数、NTT、分治/倍增
传送门 弱化版:FJOI2016 建筑师 由上面一题得到我们需要求的是\(\begin{bmatrix} N - 1 \\ A + B - 2 \end{bmatrix} \times \binom ...
随机推荐
- SpringMVC+easyUI CRUD 添加数据C
接一篇文章,今天上午实现了添加数据.以下是Jsp.里面主要是看newUser()和saveUser().注意这函数里的url,newUser()里面去掉url属性.还要注意的一个问题 <div ...
- ASP.NET导入Excel到SQL数据库
protected void btnChange_Click(object sender, EventArgs e) { UserInfoClass tClass = (UserInfoClass)S ...
- 数组,集合 转成DataTable 方法
public static DataTable ToDataTable(IList p_List) { DataTable _DataTable = new DataTable(); if (p_Li ...
- Code Complete阅读笔记(一)
代码大全也读了好几个月了,一开始读中文版,到现在慢慢尝试着读原版,确实感受到了"每天进步一点点"的魅力.遗憾的是没有从一开始就做阅读记录,总有不能尽兴和思路不清之感.确实,就像项目 ...
- iOS archive(归档)的总结
http://www.cnblogs.com/ios8/p/ios-archive.html
- 006 列表的三种删除方法 remove,pop,del
先定义一个列表: number=[,'changhao','常浩',5.2] . remove(): number.remove('changhao')---括号内是要删除的单一值 . pop(): ...
- Struts2 标签库详解2
Struts2标签库 包括: OGNL Struts2标签分类 控制标签 :(if, elseif,else, iterator, append, merge, generator, subset, ...
- YUI的UA检测
YUI.UA是针对javascript的宿主环境检测的一个检测对象,返回的是一系统关于当前宿主的信息 1.对象相关信息列表及userAgent 检测对象o = { ie: 0, //ie Mozill ...
- java.lang.ClassNotFoundException: org.apache.struts.action.ActionServlet
- 第二章IPC——IPC与开启多进程
问题 一.IPC ①.什么是IPC ②.为什么要有IPC 二.多进程 ①.如何开启多进程 ②.系统如何创建多进程 三.多进程引发的问题 问:私有进程(利用":+进程名")能否共 ...