给你一个有 n 个节点的 有向无环图(DAG),请你找出所有从节点 0 到节点 n-1 的路径并输出(不要求按特定顺序)
二维数组的第 i 个数组中的单元都表示有向图中 i 号节点所能到达的下一些节点,空就是没有下一个结点了。
译者注:有向图是有方向的,即规定了 a→b 你就不能从 b→a 。
示例 1:
输入:graph = [[1,2],[3],[3],[]]
输出:[[0,1,3],[0,2,3]]
解释:有两条路径 0 -> 1 -> 3 和 0 -> 2 -> 3
示例 2:
输入:graph = [[4,3,1],[3,2,4],[3],[4],[]]
输出:[[0,4],[0,3,4],[0,1,3,4],[0,1,2,3,4],[0,1,4]]
示例 3:
输入:graph = [[1],[]]
输出:[[0,1]]
示例 4:
输入:graph = [[1,2,3],[2],[3],[]]
输出:[[0,1,2,3],[0,2,3],[0,3]]
示例 5:
输入:graph = [[1,3],[2],[3],[]]
输出:[[0,1,2,3],[0,3]]
解析
解法很简单,以0为起点遍历图,同时记录遍历过的路径,当遍历到终点时将路径记录下来即可。
既然输入的图是无环的,我们就不需要visited数组辅助了,直接套用图的遍历框架:
1、C++语言的
class Solution {
public:
vector<vector<int>> res;
vector<int> tmp;
vector<vector<int>> allPathsSourceTarget(vector<vector<int>>& graph) {
travse(graph,0,tmp);
return res;
}
void travse(vector<vector<int>>& graph,int s,vector<int>& tmp){
int n=graph.size();
tmp.push_back(s);
if(s==n-1){
res.push_back(tmp);
tmp.pop_back();
return;
}
for(int v:graph[s]){
travse(graph,v,tmp);
}
tmp.pop_back();
}
};
2、Java语言的
class Solution {
List<List<Integer>> res=new LinkedList<>();//LinkedList是基于链表实现的
public List<List<Integer>> allPathsSourceTarget(int[][] graph) {
LinkedList<Integer> path=new LinkedList<>();
traverse(graph,0,path);
return res;
}
public void traverse(int[][] graph,int s,LinkedList<Integer> path){
path.addLast(s);// 添加节点 s 到路径,LinkedList addLast()方法
int n=graph.length;
if(s==n-1) {
res.add(new LinkedList<>(path));//!!!需要实例化
path.removeLast();//删除并返回此列表的最后一个元素
return;
}
for(int v:graph[s]){
traverse(graph,v,path);
}
path.removeLast();//移除结点s
}
}