UVA 1390 Interconnect
https://vjudge.net/problem/UVA-1390
题意:
给出n个点m条边的无向图,
每次随机加一条非自环的边,(加完后可出现重边),
添加每条边的概率是相等的
求使图连通的期望添边次数
只关心图的连通状况,即连通块的个数和大小
所以可以用{a1,a2,a3……an} 表示状态(n个连通块,每个连通块大小为ai)
添加一条边后有两种可能
1、状态不变
2、状态变为 {a1,……ai+aj,……a_n-1}
将状态哈希
dp[i]表示哈希后为i的状态 添边至连通的期望次数
dp[i]= dp[i]*p + dp[k1]*p1 + dp[k2]*p2 + …… + dp[km]*pm
其中p表示状态不变的概率,p1=Σ C(ai,2)/ C(n,2)
pi表示装移到ki这种状态的概率 ,pi= (ai*aj) / C(n,2)
上述式子移项得状态转移方程:dp[i]=(dp[k1]*p1 + dp[k2]*p2 + …… + dp[km]*pm)/(1-p)
#include<cstdio>
#include<cstring>
#include<algorithm>
const int mod=;
int n,m;
int fa[],siz[];
struct sta
{
int x[];
bool flag;
double val;
void clear() { memset(x,,sizeof(x)); }
void sort() { std::sort(x,x+); }
int hashme()
{
int v=;
for(int i=,b=;i&&x[i];i--)
{
v+=x[i]*b;
v%=mod;
b*=;
b%=mod;
}
return v;
}
bool operator == (sta b)
{
for(int i=;i<;i++)
if(x[i]!=b.x[i]) return false;
return true;
}
bool operator != (sta b)
{
return *this == b ? false : true;
}
}st,hash[mod];
int find(int i) { return fa[i]==i ? i : fa[i]=find(fa[i]); }
double gethash(sta st)
{
int x=st.hashme();
while(hash[x].flag && hash[x]!=st)
if(++x==mod) x=;
return hash[x]==st ? hash[x].val : -;
}
double inhash(sta st)
{
int x=st.hashme();
while(hash[x].flag)
if(++x==mod) x=;
hash[x]=st; hash[x].flag=true;
}
double dp(sta st)
{
if(st.hashme()==n) return ;
double x=gethash(st);
if(x!=-) return x;
double tmp=,ans=;
for(int i=;i<;i++)
tmp+=st.x[i]*(st.x[i]-)/;
for(int i=;i<;i++)
for(int j=i+;j<;j++)
{
if(!st.x[i] || !st.x[j]) continue;
sta tmp=st;
tmp.x[i]+=tmp.x[j];
tmp.x[j]=;
tmp.sort();
ans+=st.x[i]*st.x[j]*dp(tmp);
}
ans/=n*(n-)/;
ans++;
ans/=-tmp/(n*(n-)/);
st.val=ans;
inhash(st);
return ans;
}
int main()
{
int u,v;
while(scanf("%d%d",&n,&m)!=EOF)
{
for(int i=;i<mod;++i) hash[i].flag=false;
for(int i=;i<=n;i++) fa[i]=i;
while(m--)
{
scanf("%d%d",&u,&v);
fa[find(u)]=find(v);
}
st.clear();
memset(siz,,sizeof(siz));
for(int i=;i<=n;i++) siz[find(i)]++;
int tot=;
for(int i=;i<=n;i++)
if(siz[i]) st.x[tot++]=siz[i];
st.sort();
printf("%.7lf\n",dp(st));
}
}
UVA 1390 Interconnect的更多相关文章
- uva 1390 - Interconnect(期望+哈希+记忆化)
option=com_onlinejudge&Itemid=8&page=show_problem&category=514&problem=4136&mosm ...
- PatentTips - Device virtualization and assignment of interconnect devices
BACKGROUND Standard computer interconnects, particularly for personal computers or workstations, may ...
- Greenplum记录(一):主体结构、master、segments节点、interconnect、performance monitor
结构:Client--master host--interconnect--segment host 每个节点都是单独的PG数据库,要获得最佳的性能需要对每个节点进行独立优化. master上不包含任 ...
- uva 1354 Mobile Computing ——yhx
aaarticlea/png;base64,iVBORw0KGgoAAAANSUhEUgAABGcAAANuCAYAAAC7f2QuAAAgAElEQVR4nOy9XUhjWbo3vu72RRgkF5
- UVA 10564 Paths through the Hourglass[DP 打印]
UVA - 10564 Paths through the Hourglass 题意: 要求从第一层走到最下面一层,只能往左下或右下走 问有多少条路径之和刚好等于S? 如果有的话,输出字典序最小的路径 ...
- UVA 11404 Palindromic Subsequence[DP LCS 打印]
UVA - 11404 Palindromic Subsequence 题意:一个字符串,删去0个或多个字符,输出字典序最小且最长的回文字符串 不要求路径区间DP都可以做 然而要字典序最小 倒过来求L ...
- UVA&&POJ离散概率与数学期望入门练习[4]
POJ3869 Headshot 题意:给出左轮手枪的子弹序列,打了一枪没子弹,要使下一枪也没子弹概率最大应该rotate还是shoot 条件概率,|00|/(|00|+|01|)和|0|/n谁大的问 ...
- UVA计数方法练习[3]
UVA - 11538 Chess Queen 题意:n*m放置两个互相攻击的后的方案数 分开讨论行 列 两条对角线 一个求和式 可以化简后计算 // // main.cpp // uva11538 ...
- UVA数学入门训练Round1[6]
UVA - 11388 GCD LCM 题意:输入g和l,找到a和b,gcd(a,b)=g,lacm(a,b)=l,a<b且a最小 g不能整除l时无解,否则一定g,l最小 #include &l ...
随机推荐
- 动态规划——最长公共子序列LCS及模板
摘自 https://www.cnblogs.com/hapjin/p/5572483.html 这位大佬写的对理解DP也很有帮助,我就直接摘抄过来了,代码部分来自我做过的题 一,问题描述 给定两个字 ...
- 吴恩达机器学习笔记——正规方程(Normal Equation)
问题描述:m examples : (x(1),y(1)), (x(2),y(2)),..., (x(m),y(m)) and n features; 计算方法:θ = (XTX)-1XTy; 计算过 ...
- Scrum立会报告+燃尽图(Beta阶段第七次)
此作业要求参见:https://edu.cnblogs.com/campus/nenu/2018fall/homework/2388 项目地址:https://coding.net/u/wuyy694 ...
- 互评Alpha版本 - Hello World团队项目空天猎
在测评该项目时,我找到了Hello World!团队的git,并下载了相关文件以及阅读了程序运行说明. 如图所示,我下载了一个名为 SkyHunter1.0.rar 的压缩文件包,文件包内容如下: 根 ...
- 如何利用Xshell在Linux下安装jdk
本文会详细介绍如何在Linux下安装JDK1.8 首先要设置虚拟机的IP地址,不知道如何设置的话可以 翻看我的前一篇博客 http://www.cnblogs.com/xiaoxiaoSMILE/ ...
- C++进阶之_类型转换
C++进阶之_类型转换 1.类型转换名称和语法 C风格的强制类型转换(Type Cast)很简单,不管什么类型的转换统统是: TYPE b = (TYPE)a C++风格的类型转换提供了4种类型转换操 ...
- 1106C程序语法树
- [转帖] 部分收费的Oracle JDK VS 完全免费的OpenJDK
来源: http://www.flammulina.com/2018/10/28/%E9%83%A8%E5%88%86%E6%94%B6%E8%B4%B9%E7%9A%84oracle-jdk-vs- ...
- 【C】树
1.子树是不相交的 2.除了根节点,每个节点有且仅有一个父节点 3.一颗n个节点的树有n-1条边 儿子兄弟表示法 满二叉树与完全二叉树 1.满二叉树是除了叶子节点,每一个节点都有两个子节点,并按顺序排 ...
- Thread的run()与start()的区别
java的线程是通过java.lang.Thread类来实现的.VM启动时会有一个由主方法所定义的线程.可以通过创建Thread的实例来创建新的线程.每个线程都是通过某个特定Thread对象所对应的方 ...