AtCoder Beginner Contest 244 E - King Bombe

AtCoder Beginner Contest 244 E - King Bombe

题意:

给出一个简单无向图,一共有n个点m条边。

先需要从点 s 走到 点 t,走的过程中经过的点恰好经过k条边,并且需要经过点 x 偶数次(可以为0次)。

求解方案数。

思路:

假如我们不去考虑经过点 x这个附加条件,仅考虑前半部分。

那么我们可以用dp状态转移方程表示该过程。

\(dp[i][j]\)表示从点 s 走到点 j 经过 i 条边

\(dp[0][j]=1 \quad (j==s)\)

\(dp[0][j]=0 \quad (j\neq s)\)

\(dp[i+1][j] = \sum_{k\in adj(j)} dp[i][k]\)

现在将偶数这个条件加进来考虑,可以发现,每一次行走,如果在两个非x点之间行走,那么经过x的次数time的奇偶不会发生变化,如果从一个点走到 x ,那么此时的奇偶会发生变化,也就相当于将经过x的次数time去mod 2,那么也就剩下0,1两种情况。

\(dp[i][j][t]\) 表示从点 s 走到点 j 经过 i 条边 并且 经过x的次次数mod 2 = t。即t=0为偶数次,t=1为奇数次。

\(dp[0][j][0]=1 \quad (j==s)\)

\(dp[0][j][0]=0 \quad (j\neq s)\)

\(dp[0][j][1]=0\)

\(dp[i+1][j][t] = \sum_{k\in adj(j)} dp[i][k][t](j \neq x)\)

\(dp[i+1][x][t] = \sum_{k\in adj(x)} dp[i][k][1-t]\)

#include<bits/stdc++.h>
#define pii pair<int,int>
#define ll    long long
#define ull unsigned long long
using namespace std;
const ll inf =0x3f3f3f3f3f;
const ll mod =998244353;
const int N=5005;
ll qpow(ll a,ll p){ll ans=1;while(p){if(p&1)ans=ans*a%mod;a=a*a%mod;p>>=1;}return ans%mod;}

int n,m,k,s,t,x;
ll dp[N][N][2];
vector<pair<int,int>>g;
void solve(){ 
    cin>>n>>m>>k>>s>>t>>x;
    for(int i=1;i<=m;i++){
        int u,v;cin>>u>>v;
        g.push_back({u,v});
   }
   dp[0][s][0]=1;
    for(int i=0;i<k;i++){
        for(auto [u,v]:g){
            for(int t=0;t<=1;t++){
                dp[i+1][v][t^(v==x)]=(dp[i+1][v][t^(v==x)]+dp[i][u][t])%mod;
                dp[i+1][u][t^(u==x)]=(dp[i+1][u][t^(u==x)]+dp[i][v][t])%mod;
            }
        }
    }
    cout<<dp[k][t][0]%mod<<endl;
}
int main(){
    ios::sync_with_stdio(0);cin.tie(0);cout.tie(0);
    int kase=1;
   // cin>>kase;
    while(kase--){solve();}
}

posted @ 2022-03-21 00:00  LiAnG24  阅读(51)  评论(0)    收藏  举报