在一个有向图中,节点分别标记为 0, 1, …, n-1。图中每条边为红色或者蓝色,且存在自环或平行边。
red_edges 中的每一个 [i, j] 对表示从节点 i 到节点 j 的红色有向边。类似地,blue_edges 中的每一个 [i, j] 对表示从节点 i 到节点 j 的蓝色有向边。
返回长度为 n 的数组 answer,其中 answer[X] 是从节点 0 到节点 X 的红色边和蓝色边交替出现的最短路径的长度。如果不存在这样的路径,那么 answer[x] = -1。
示例 1:
输入:n = 3, red_edges = [[0,1],[1,2]], blue_edges = []
输出:[0,1,-1]
示例 2:
输入:n = 3, red_edges = [[0,1]], blue_edges = [[2,1]]
输出:[0,1,-1]
示例 3:
输入:n = 3, red_edges = [[1,0]], blue_edges = [[2,1]]
输出:[0,-1,-1]
示例 4:
输入:n = 3, red_edges = [[0,1]], blue_edges = [[1,2]]
输出:[0,1,2]
示例 5:
输入:n = 3, red_edges = [[0,1],[0,2]], blue_edges = [[1,0]]
输出:[0,1,1]
来源:力扣(LeetCode)
链接:https://leetcode.cn/problems/shortest-path-with-alternating-colors
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。
一个位置有两种状态,红色是否访问和蓝色是否访问,如果只用一个used_node肯定不行。
class Solution {
public:
vector<int> shortestAlternatingPaths(int n, vector<vector<int>>& redEdges, vector<vector<int>>& blueEdges) {
vector<vector<int>> red(n, vector<int>());
auto blue = red;
unordered_set<int> red_set, blue_set;
vector<int> ret(n, -1);
if (n < 1) return ret;
for (auto vec : redEdges) {
red[vec[0]].push_back(vec[1]);
}
for (auto vec : blueEdges) {
blue[vec[0]].push_back(vec[1]);
}
queue<pair<int, bool>> bfs; //<true是红
bfs.push({0, true});
bfs.push({0, false});
red_set.insert(0);
blue_set.insert(0);
ret[0] = 0;
int count = 0;
while (!bfs.empty()) {
queue<pair<int, bool>> bfs_tmp;
bfs_tmp.swap(bfs);
++count;
while (!bfs_tmp.empty()) {
auto pos_pair = bfs_tmp.front();
bfs_tmp.pop();
if (pos_pair.second) { //<当前是红
for (auto value : blue[pos_pair.first]) {
if (blue_set.find(value) == blue_set.end()) {
bfs.push({value, false});
blue_set.insert(value);
}
if (ret[value] == -1) {
ret[value] = count;
}
}
} else {
for (auto value : red[pos_pair.first]) {
if (red_set.find(value) == red_set.end()) {
bfs.push({value, true});
red_set.insert(value);
}
if (ret[value] == -1) {
ret[value] = count;
}
}
}
}
}
return ret;
}
};