力扣797. 所有可能的路径

第九十一天 --- 力扣797. 所有可能的路径

题目一

力扣:797. 所有可能的路径

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

思路

一道经典的图论从源点到汇点求路径问题
1、读懂题目,他给的数据形式很简单,非常实用,总结一句话就是,gragh[0]存的就是第0个点直接和哪些点相连,很适合求路径使用。

BFS

1、提到BFS,我们第一反应就是用队列维护。
2、但是平常的都是用队列维护一个个的点,这个题要求出所有的路径,问题变化了,我要求所有的源点到汇点的路径,我们发现单纯的用维护点的方法行不通了,不适合维护路径。
3、所以我们大胆点,每次都用队列维护当前路径即可,每次弹出的路径的最后一个元素就是上一次新加入的,用那个点继续扩展即可。别的思路都一样,既然要求路径,我就用队列维护路径就好了。

DFS:经典回溯思路

1、这个没什么好说的,有向无环图,不存在死循环,不用visit数组标识是否走过。
2、dfs的时候,到终点,当前维护的全局tmp直接压入答案即可,每扩展到一个点,将之压入全局tmp临时路径,当该点对应的路径都找完了,回溯回来的时候(即该点对应的dfs结束),那么这个点无用了(因为这个点扩充的路径没了),所以从tmp中删除,这么做也因为tmp临时路径是全局的。

代码

BFS

1、注意,一定要随应变,既然求的是路径,那么就直接维护路径好了

class Solution {
    
    
public:
	vector<vector<int>> ans;
	vector<vector<int>> allPathsSourceTarget(vector<vector<int>>& graph) {
    
    
		int n = graph.size();
		queue<vector<int>> item;
		vector<int> tmp;
		tmp.push_back(0);//初始化
		item.push(tmp);
		while (!item.empty()) {
    
    
			vector<int> point = item.front();//弹出路径
			item.pop();

			int p1 = point[point.size() - 1];//最后一个点是上一次新来的点,用这个点进行扩充
			if (p1 == n - 1) {
    
    //走到终点
				ans.push_back(point);
				continue;//说明这个路径没用了,继续循环
			}
			for (int p : graph[p1]) {
    
    
				vector<int> tmps(point);//进行点的扩充
				tmps.push_back(p);
				item.push(tmps);
			}
		}
		return ans;
	}
};

所有代码均以通过力扣测试
(经过多次测试最短时间为):
在这里插入图片描述

DFS

class Solution {
    
    
public:
	vector<vector<int>> graph;
	int n;

	vector<vector<int>> ans;
	vector<int> tmp;

	void dfs(int point) {
    
    
		if (point == n - 1) {
    
    
			ans.push_back(tmp);
			return;
		}
		for (int p : graph[point]) {
    
    
			tmp.push_back(p);
			dfs(p);
			tmp.pop_back();
		}
	}

	vector<vector<int>> allPathsSourceTarget(vector<vector<int>>& graph) {
    
    
		n = graph.size();
		this->graph = graph;
		tmp.push_back(0);
		dfs(0);
		return ans;
	}
};

所有代码均以通过力扣测试
(经过多次测试最短时间为):

在这里插入图片描述
在这里插入图片描述

Guess you like

Origin blog.csdn.net/qq_45678698/article/details/121043628