求助,80分,为啥这份代码超时4个点
查看原帖
求助,80分,为啥这份代码超时4个点
52421
LQHqwq楼主2022/12/4 13:43

用的是缩点+DP

#include<bits/stdc++.h>
#define ll long long
#define llINF 0x7FFFFFFFFFFFFFFF
#define intINF 0x7fffffff
using namespace std;
const int maxn = 1e6+5;
const ll mod = 1e9+7;
struct edge{
    ll u,v;
};
vector<edge> e;
vector<ll> h[maxn];
struct node{
    ll x,y,point,road,v;
} p[maxn];
ll tot=1,dfn[maxn],low[maxn],idx,scc[maxn],stot,if_bri[2000005];
ll vis[maxn],ans=1,dp[2][maxn],w[maxn],sizp[maxn],sizr[maxn],n,m,a,b;
vector<ll> g[maxn];
vector<node> bri;
void add(ll x,ll y){
    e.push_back({x,y});
    h[x].push_back(e.size()-1);
}
ll qsm(ll a,ll x){
    ll s = 1;
    while(x){
        if(x & 1) s = s * a % mod;
        a = a * a % mod;
        x >>= 1;
    }
    return s % mod;
}
void tarjan(ll x,ll ine){
    dfn[x] = low[x] = ++idx;
    for(int i = 0; i < h[x].size(); ++i){
        ll j = h[x][i], y = e[j].v;
        if(!dfn[y]){
            tarjan(y,j);
            low[x] = min(low[x],low[y]);
            if(dfn[x] < low[y]) {
                if_bri[j] = if_bri[j^1] = 1;
                bri.push_back({x,y});
            }
        }
        else if(j != (ine ^ 1)) 
            low[x] = min(low[x],dfn[y]);
    }
}
void dfs(ll x,ll ine,ll &point,ll &road){
    scc[x] = stot;
    point++;
    for(int i = 0; i < h[x].size(); ++i){
        ll j = h[x][i], y = e[j].v;
        if(!if_bri[j]) road++;
        if(if_bri[j] || scc[y]) continue;  
        dfs(y,j,point,road);    
    }
}
void dfs1(int x,int fa){
    dp[0][x] = p[x].v;
    dp[1][x] = 0;
    sizr[x] = p[x].road;
    vis[x] = 1;
    ll t = 0,sum = 1;
    for(int y : g[x]){
        if(y == fa) continue;
        if(!t) t = 1;
        dfs1(y,x);
        sizr[x] += sizr[y] + 1;
        t = t * (dp[0][y] + 2*qsm(2,sizr[y])) % mod;
        sum = sum*2%mod*qsm(2,sizr[y])%mod;
    }
    if(t) dp[0][x] = qsm(2,p[x].road)*(((t - sum)%mod+mod) % mod) % mod + p[x].v * t % mod; 
    for(int y : g[x]){
        if(y == fa) continue;
        dp[1][x] = (dp[1][x] + (dp[0][y]*qsm(2,sizr[x]-sizr[y]-1)%mod + dp[1][y]*qsm(2,sizr[x]-sizr[y])%mod))%mod;
    }
}
int main(){
    cin >> n >> m;
    for(int i = 1; i <= m; ++i){
        cin >> a >> b;
        add(a,b),add(b,a);
    }
    for(int i = 1; i <= n; ++i)
        if(!dfn[i]) tarjan(i,0);
    
    for(int i = 1; i <= n; ++i){
        if(!scc[i]){
            ++stot;
            dfs(i,0,p[stot].point,p[stot].road);
            p[stot].road /= 2;
            p[stot].v = (qsm(2,p[stot].point)-1) % mod * qsm(2,p[stot].road) % mod;
        }
    }
    for(int i = 0; i < bri.size(); ++i){
        g[scc[bri[i].x]].push_back(scc[bri[i].y]);
        g[scc[bri[i].y]].push_back(scc[bri[i].x]);
    }
    for(ll i = 1; i <= stot; ++i) {
        if(vis[i]) continue;
        dfs1(i,i);
        ans = ans*((dp[0][i]+dp[1][i])%mod)%mod;
    }
    cout << ans << endl;
    return 0;
}
2022/12/4 13:43
加载中...