问题:路径其实既可以在bfs树的两条不同路径上,也可以在在dfs树的两条不同路径上,但是切记不要广搜一边搜一边查找答案,会导致查找错误的,因为你访问的点还不一定已经构造完成(这么简单的问题都没发现,唉。。。)

题解:

  从起点s出发构造一棵树,如果有答案的话,我们会发现除终点外,两条路径一定在两棵不同的子树中,所以只需要枚举除s外的点,看它是否有一条边与其他子树相连。

所以先广搜一遍构造一棵树,然后再广搜一遍靠反边来查找答案。

#include<iostream>
#include<cstdio>
#include<cstring>
#include<cstdlib>
#include<algorithm>
#include<vector>
#include<queue>
#define maxn 200009
using namespace std;
vector<int>v1[maxn],v2[maxn];
bool vis[maxn];
int fa[maxn],num[maxn];
queue<int>q;
int st,n,m,cnt,ans[maxn];
void dfs(int x)
{
    ans[++cnt]=x;
    if (fa[x]!=x) dfs(fa[x]);
}
void work()
{
    int len=v1[st].size();
    for (int i=1;i<=n;i++) vis[i]=false,fa[i]=i,num[i]=i;
    vis[st]=true;
    for (int i=0;i<len;i++) 
    {
        int to=v1[st][i];
        q.push(to);
        fa[to]=st;
        vis[to]=true;
    }
    while (!q.empty())
    {
        int now=q.front(); q.pop();
        len=v1[now].size();
        for (int i=0;i<len;i++)
        {
            int to=v1[now][i];
            if (vis[to]) continue;
            vis[to]=true;
            num[to]=num[now];
            fa[to]=now;
            q.push(to);
        }
    } 
    for (int i=1;i<=n;i++)
    {
        if (i==st) continue;
        int len=v2[i].size();
        for (int j=0;j<len;j++)
        {
            int to=v2[i][j];
            if (fa[i]==to)    continue;    
            if ((vis[to])&&(num[to]!=num[i])) 
            {
                cout<<"Possible"<<endl;
                cnt=1; ans[1]=i; dfs(to); 
                cout<<cnt<<endl;
                for (int k=cnt;k>=1;k--) cout<<ans[k]<<" \n"[k==1];
                cnt=0; dfs(i); 
                cout<<cnt<<endl;
                for (int k=cnt;k>=1;k--) cout<<ans[k]<<" \n"[k==1];
                return;
            }
        }
    }
    cout<<"Impossible"<<endl;
}
int main()
{
    cin>>n>>m>>st;
    int x,y;
    for (int i=1;i<=m;i++)
    {
        cin>>x>>y;
        v1[x].push_back(y);
        v2[y].push_back(x);
    }
    work();
    return 0;
}

 

posted on 2022-04-14 17:29  nhc2014  阅读(60)  评论(0编辑  收藏  举报