L3-025 那就别担心了 (30 分)
思路:dfs+剪枝,对于某一个已经跑过的点,可以记录它的答案,下一次再询问它的时候,直接取答案就行,不需要再dfs这个点了
坑:如果此时是这副图,且起点和终点分别是1和3,那么也要输出yes。
“从某个命题出发的所有推理路径都会将结论引导到同一个最终命题”这句话,并不是要走到底,只要走到终点就要停下来。。。,所以只要设置vis[end]=1就行了
代码:
int n, m;
vector<int> G[502];
int s, t;
int p=1; // 记录是否存在其他终点
int vis[502];
int dfs(int u){
if(G[u].empty()){
if(u!=t) p=0, vis[u]=0; // 如果是终点,但不是我们想要的终点,那么就要输出No
else vis[u]=1;
return vis[u];
}
int sum=0;
for(int v:G[u]){
if(vis[v]==-1) dfs(v); // 如果某个点已经有答案直接返回,否则dfs
sum+=vis[v];
}
return vis[u]=sum;
}
void work(){
cin>>n>>m;
memset(vis, -1, sizeof vis); // -1 标记该点没有跑过
for(int i=1;i<=m;++i){
int u, v; cin>>u>>v;
G[u].push_back(v);
}
cin>>s>>t;
vis[t]=1; // 坑死我了
cout<<dfs(s)<<' '<<(p? "Yes":"No");
}