【2014】

D2T2  finding your way

Compared to the code a test of thinking ability even more questions.

First, we must recognize the special nature only related with the end, running a reverse map is a very common operation.

So this question is to start our end run again reverse drawing, to be able to reach the end point marked as the last point on the path is definitely selected from these points, special attention sentence if the starting point run no end in sight to direct output - 1 and return 0.

Next enumerated reach the end point, which are marked as first point on the path, and then enumerate each end side thereof, the (current point corresponding to the enumeration) does not reach the end of a given topic in the end, then to remove the marked point mark, indicating that it can not appear on the path.

Finally bfs run a shortest path, only to run the marked point.

#include<bits/stdc++.h>
#define ri register int
#define ll long long
#define For(i,l,r) for(ri i=l;i<=r;i++)
#define Dfor(i,r,l) for(ri i=r;i>=l;i--)
using namespace std;
const int M=1e5+5;
int dis[M],n,m,a,b,s,t;
bool path[M],can[M];
vector<int>side[M];
vector<int>edis[M];
queue<int>q;
inline ll read(){
    ll f=1,sum=0;
    char ch=getchar();
    while(!isdigit(ch)){if(ch=='-')f=-1;ch=getchar();}
    while(isdigit(ch)){sum=(sum<<1)+(sum<<3)+(ch^48);ch=getchar();}
    return f*sum;
}
int main(){
    n=read(),m=read();
    For(i,1,m){
        a=read(),b=read();
        side[a].push_back(b);
        edis[b].push_back(a);
    }
    s=read(),t=read();
    can[t]=1;q.push(t);
    while(!q.empty()){
        int u=q.front();q.pop();
        for(int i=edis[u].size()-1;i>=0;i--){
            int v=edis[u][i];
            if(!can[v]){
                can[v]=1;
                q.push(v);
            }
        }
    }
    if(!can[s]){printf("-1\n");return 0;}
    For(i,1,n){
        if(can[i]){
            path[i]=1;
            for(int j=side[i].size()-1;j>=0;j--){
                int v=side[i][j];
                if(!can[v]){
                    path[i]=0;
                    break;
                }
            }
        }
    }
    if(!path[s]){printf("-1\n");return 0;}
    dis[s]=1;q.push(s);
    while(!q.empty()){
        int u=q.front();q.pop();
        if(u==t){printf("%d\n",dis[t]-1);return 0;}
        for(int i=side[u].size()-1;i>=0;i--){
            int v=side[u][i];
            if(path[v]&&!dis[v]){
                dis[v]=dis[u]+1;
                q.push(v);
            }
        }
    }
    printf("-1\n");
    return 0;
}
View Code

 

 

 

Guess you like

Origin www.cnblogs.com/jian-song/p/11867767.html