• BZOJ 4031 [HEOI2015]小Z的房间(Matrix-Tree定理)


    【题目链接】 http://www.lydsy.com/JudgeOnline/problem.php?id=4031

    【题目大意】

      你突然有了一个大房子,房子里面有一些房间。
      事实上,你的房子可以看做是一个包含n*m个格子的格状矩形,
      每个格子是一个房间或者是一个柱子。在一开始的时候,相邻的格子之间都有墙隔着。
      你想要打通一些相邻房间的墙,使得所有房间能够互相到达。
      在此过程中,你不能把房子给打穿,或者打通柱子(以及柱子旁边的墙)。
      同时,你不希望在房子中有小偷的时候会很难抓,
      所以你希望任意两个房间之间都只有一条通路。现在,你希望统计一共有多少种可行的方案。

    【题解】

      根据任意两个房间之间只有一条通路我们可以知道这题要求的是生成树的方案数,
      那么我们先求出这个图的基尔霍夫矩阵,然后求余子式就是答案,处理一下取模即可。

    【代码】

    #include <cstdio>
    #include <algorithm>
    using namespace std;
    typedef long long LL;
    #define rep(i,n,m) for(int i=n;i<=m;i++)
    const LL mod=1000000000;
    int dx[]={0,0,1,-1},dy[]={1,-1,0,0};
    int n,m,id;
    char mp[110][110];
    LL a[110][110],p[110][110];
    int det(int n){
        LL ans=1,f=1;
        rep(i,1,n)rep(j,1,n)a[i][j]=(a[i][j]+mod)%mod;
        rep(i,1,n){
            rep(j,i+1,n){
                LL A=a[i][i],B=a[j][i];
                while(B!=0){
                    LL t=A/B; A%=B; swap(A,B);
                    for(int k=1;k<=n;k++)a[i][k]=(a[i][k]-t*a[j][k]%mod+mod)%mod;
                    for(int k=1;k<=n;k++)swap(a[i][k],a[j][k]);
                    f=-f;
                }
            }if(!a[i][i])return 0;
            ans=ans*a[i][i]%mod;
        }if(f==-1)return (mod-ans)%mod;
        return ans;
    }
    bool check(int x,int y){if(x<1||y<1||x>n||y>m||mp[x][y]!='.')return 0;return 1;}
    int main(){
        scanf("%d%d",&n,&m);
        rep(i,1,n)scanf("%s",mp[i]+1);
        rep(i,1,n)rep(j,1,m)if(mp[i][j]=='.')p[i][j]=++id;
        rep(i,1,n)rep(j,1,m)if(mp[i][j]=='.'){
            rep(k,0,4){
                int x=i+dx[k],y=j+dy[k];
                if(check(x,y)){int u=p[i][j],v=p[x][y];a[u][u]++;a[u][v]--;}
            }
        }printf("%d
    ",det(id-1));
        return 0;
    }
  • 相关阅读:
    string与stringbuilder的区别
    Web负载均衡的几种实现方式
    JS 禁用鼠标右键
    JS中的!=、== 、!==、===的用法和区别。
    SQL Server Change Tracking
    关于更新发布CSS和JS文件的缓存问题
    Authorization in Cloud Applications using AD Groups
    英语学习[ZZ]
    我奋斗了18年,不是为了和你一起喝咖啡
    我奋斗了18年才和你坐在一起喝咖啡
  • 原文地址:https://www.cnblogs.com/forever97/p/bzoj4031.html
Copyright © 2020-2023  润新知