[基环] codeforces 711D. Directed Roads

原创 2016年08月30日 14:39:58

Directed Roads

题意:

给n个点,和P[i],表示从第i个点到P[i]有一条有向边,每条边可以至多翻转方向一次,问有多少种方法翻转后没有环。

思路:

n个点n条边,无自环,每点出度为1,这个模型应该也出过很多次了。
这个图要么就是一整个环,要么就是一个环加一棵树,要么就是前面的复制几次。
考虑一个连通块,将它分为环上的边x和环外的边y,可以看出环外的边随便翻转都不形成环,所以任意翻转,答案是2|y|,环上的任意翻转会有顺时针和逆时针两种环,所以答案是2|x|2,一个连通块的答案就是2|y|(2|x|2),多个连通块相互独立,直接乘起来就行。

#include<bits/stdc++.h>
using namespace std;
const int N = 2e5+5;
typedef long long ll;
const ll mod = 1e9+7;
vector<int>G[N];
int in[N];
bool hs[N];
ll qpow(ll a, ll k){
    ll res = 1;
    while(k){
        if(k&1) res = (res*a)%mod;
        a = (a*a)%mod;
        k >>= 1;
    }
    return res;
}
ll solve(int rt){
    int all = 0;
    queue<int>q, qq;
    q.push(rt); hs[rt] = 1;
    while(!q.empty()){
        int u = q.front(); q.pop();
        all++;
        if(in[u] == 1) qq.push(u);
        for(int v : G[u]){
            if(!hs[v]){
                hs[v] = 1;
                q.push(v);
            }
        }
    }
    int ciy = all;
    while(!qq.empty()){
        int u = qq.front(); qq.pop();
        --ciy;
        for(int v : G[u]){
            if((--in[v]) == 1) qq.push(v);
        }
    }
    return qpow(2, all-ciy)*((qpow(2, ciy)-2+mod)%mod)%mod;
}
int main(){
    int n;
    scanf("%d", &n);
    ll ans = 1;
    for(int x, i = 1; i <= n; ++i){
        scanf("%d", &x);
        G[x].push_back(i);
        G[i].push_back(x);
        in[x]++, in[i]++;
    }
    for(int i = 1; i <= n; ++i){
        if(hs[i]) continue;
        ans = ans*solve(i)%mod;
    }
    printf("%lld\n", ans);
}
版权声明:本文为博主原创文章,未经博主允许不得转载。

相关文章推荐

Codeforces Problem 711D Directed Roads(Tarjan判环)

Codeforces Problem 711D Directed Roads(Tarjan判环)

CodeForces - 711D Directed Roads(dfs判环)

Directed RoadsZS the Coder and Chris the Baboon has explored Udayland for quite some time. They real...

Codeforces 711D Directed Roads(所有点出度为1的图反向边去环)

D. Directed Roads time limit per test 2 seconds memory limit per test 256 megabytes input...
  • Yasola
  • Yasola
  • 2016年08月30日 12:53
  • 554

【34.40%】【codeforces 711D】Directed Roads

time limit per test2 seconds memory limit per test256 megabytes inputstandard input outputstandar...

Codeforces 711D Directed Roads

ZS the Coder and Chris the Baboon has explored Udayland for quite some time. They realize that it co...
  • nare123
  • nare123
  • 2016年09月06日 22:25
  • 130

Codeforces711D-Directed Roads(强连通分量+乘法原理)

题目链接http://codeforces.com/contest/711/problem/D思路这道题的输入很神奇,由输入可以得出一个结论就是每个点最多只会有一条出边,因此每个点最多在一个环中。 ...
  • Lzedo
  • Lzedo
  • 2016年09月23日 20:46
  • 165

Codeforces Round #369 (Div. 2) -- D. Directed Roads (DFS找环)

大体题意: 给你一个有向图,可能会有环,你的操作是反向一条路,求得使得图中没有环所有方案数? 思路: 假如图中没有环的话,有n条边,答案就是2^n 如果有个m边的环,间接法考虑,总方案是2^m...

Codeforces Round #369 (Div. 2) D. Directed Roads (dfs+组合数学 图论)

传送门:D. Directed Roads 描述: D. Directed Roads time limit per test 2 seconds memory li...

Codeforces #369 div2 D.Directed Roads

codeforces

[Codeforces Round #369 (Div. 2)D. Directed Roads]Tarjan强连通分量+组合计数

[Codeforces Round #369 (Div. 2)D. Directed Roads]Tarjan强连通分量题目链接:[Codeforces Round #369 (Div. 2)D. D...
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:[基环] codeforces 711D. Directed Roads
举报原因:
原因补充:

(最多只允许输入30个字)