zoukankan      html  css  js  c++  java
  • CF1540B Tree Array 题解

    Codeforces
    Luogu

    Description.

    给定一棵树,约定一个序列 \(\{a_i\}\) 是合法的,当且仅当:

    • \(\forall i\in[1,n],\exists j\in[1,i),(a_i,a_j)\in\mathbf G\)

    一个序列的价值定义为逆序对数,求价值期望。

    Solution.

    逆序对没有什么优美的性质。
    所以我们考虑把期望拆成 \(i\ge j\),在序列中 \(i\) 排在 \(j\) 前面的概率和。
    然后发现第一个点没有什么限制,和后面不同,考虑枚举第一个点。
    接下来我们需要判断取到 \(x\) 在取到 \(y\) 前的概率。
    首先我们发现直到 \(\text{LCA}(x,y)\),都不会对概率造成影响。
    取其他的元素也不会对这个概率造成影响,因为它是概率。
    问题转化成了给两个数,每次有一半的概率给第一个数减一,一半的概率给第二个数减一。
    发现问题维度是 \(2\) 维的,直接做一个 \(O(n^2)\)dp 预处理即可。
    因为我们枚举了 \(a_1\),所以还需要乘上 \(\frac 1n\)

    Coding.

    点击查看代码
    //是啊,你就是那只鬼了,所以被你碰到以后,就轮到我变成鬼了{{{
    #include<bits/stdc++.h>
    using namespace std;typedef long long ll;
    template<typename T>inline void read(T &x)
    {
    	x=0;char c=getchar(),f=0;
    	for(;c<48||c>57;c=getchar()) if(!(c^45)) f=1;
    	for(;c>=48&&c<=57;c=getchar()) x=(x<<1)+(x<<3)+(c^48);
    	f?x=-x:x;
    }
    template<typename T,typename...L>inline void read(T &x,L&...l) {read(x),read(l...);}/*}}}*/
    const int P=1e9+7,I2=(P+1)>>1;char lcv[205];int dp[205][205];
    inline int ksm(int x,int q=P-2) {int r=1;for(;q;q>>=1,x=1ll*x*x%P) if(q&1) r=1ll*r*x%P;return r;}
    struct edge{int to,nxt;}e[405];int et,head[205],n,lc[205][205],dep[205];
    inline void adde(int x,int y) {e[++et]=(edge){y,head[x]},head[x]=et;}
    inline void dfs0(int x,int fa)
    {
    	for(int i=1;i<=n;i++) if(lcv[i]) lc[i][x]=lc[x][i]=lc[fa][i];
    	lcv[x]=1,lc[x][x]=x,dep[x]=dep[fa]+1;
    	for(int i=head[x];i;i=e[i].nxt) if(e[i].to!=fa) dfs0(e[i].to,x);
    }
    int main()
    {
    	read(n);for(int i=1,x,y;i<n;i++) read(x,y),adde(x,y),adde(y,x);
    	for(int i=0;i<=n;i++) dp[0][i]=1;
    	for(int i=1;i<=n;i++) for(int j=1;j<=n;j++) dp[i][j]=1ll*(dp[i-1][j]+dp[i][j-1])*I2%P;
    	//for(int i=0;i<=n;i++) for(int j=0;j<=n;j++) printf("%d%c",dp[i][j],j==n?'\n':'\t');
    	int rs=0;for(int rt=1;rt<=n;rt++)
    	{
    		dfs0(rt,0);for(int x=1,l;x<=n;x++) for(int y=1;y<x;y++)
    			l=lc[x][y],rs=(rs+dp[dep[x]-dep[l]][dep[y]-dep[l]])%P;
    	}
    	return printf("%lld\n",1ll*rs*ksm(n)%P),0;
    }
    
  • 相关阅读:
    2019-1-17水晶报表函数大全
    2019-1-17【水晶报表内功心法】--推拉之间
    2019-1-17水晶报表技巧总结【二】
    2019-1-16 水晶报表自动补空行
    2019-1-16水晶报表技巧总结【一】
    博客园添加访客人数
    2019-1-11存储过程的查看
    2019-1-11数据库重构
    lcx端口转发 linux版
    PentesterLab-From SQL Injection to Shell: PostgreSQL edition
  • 原文地址:https://www.cnblogs.com/pealfrog/p/15173318.html
Copyright © 2011-2022 走看看