codeforces1472G Moving to the Capital(spfa变形)

Portal
Solution: First of all, after seeing the meaning of the question, I found that this question is quite similar to cf1473E . First, calculate the ddd value, run abfs bfsb f s , and then considerans [i] [0/1] ans[i][0/1]A n- S [ I ] [ 0 / . 1 ] represents a starting point foriiThere is no2 2in the path of i2 operations and there are1 11 time2 22 The smallestddthat can be reached in the path of operationd value, so the update is actually simple. Consider an edge asi −> j i->ji>j,那么
i f ( d [ i ] < d [ j ] )   a n s [ i ] [ 0 ] = m i n ( a n s [ i ] [ 0 ] , a n s [ j ] [ 0 ] ) , a n s [ i ] [ 1 ] = m i n ( a n s [ i ] [ 1 ] , a n s [ j ] [ 1 ] ) e l s e   a n s [ i ] [ 1 ] = m i n ( a n s [ i ] [ 1 ] , a n s [ j ] [ 0 ] ) if(d[i]<d[j])\ ans[i][0]=min(ans[i][0],ans[j][0]),ans[i][1]=min(ans[i][1],ans[j][1])\\ else\ ans[i][1]=min(ans[i][1],ans[j][0])\\ if(d[i]<d [ j ] ) a n s [ i ] [ 0 ] =m i n ( a n s [ i ] [ 0 ] ,a n s [ j ] [ 0 ] ) ,a n s [ i ] [ 1 ]=m i n ( a n s [ i ] [ 1 ] ,a n s [ j ] [ 1 ] )e l s e a n s [ i ] [ 1 ] =m i n ( a n s [ i ] [ 1 ] ,a n s [ j ] [ 0 ] )
Then consider building an inverse graph, and then press all the initial values ​​into set sets e t , and then began tospfa spfas p f a until there is no update.
In the codeans [i] [0] ans[i][0]ans[i][0] 表示为 d [ i ] . f i r s t d[i].first d[i].first a n s [ i ] [ 1 ] ans[i][1] a n s [ i ] [ 1 ] is expressed asd [i]. secondd[i].secondd[i].second .

#include <bits/stdc++.h>
using namespace std;
const int inf = 0x3f3f3f3f;
int main()
{
    
    
    int T;
    cin >> T;
    while (T--) {
    
    
        int n, m;
        cin >> n >> m;
        vector<int> g[n], rg[n];
        for (int i = 0, u, v; i < m; i++) {
    
    
            cin >> u >> v;
            u--; v--;
            g[u].emplace_back(v);
            rg[v].emplace_back(u);
        }
        vector<int> dis(n);
        vector<pair<int, int>> d(n, {
    
    inf, inf});
        queue<pair<int, int>> q;
        d[0].first = 0;
        dis[0] = 0;
        set<pair<int, pair<int, int>>> s;
        q.push({
    
    0, 0});
        s.insert({
    
    0, {
    
    0, 0}});
        while (!q.empty()) {
    
    
            int u = q.front().first, w = q.front().second;
            q.pop();
            for (auto x : g[u]) {
    
    
                if (x == 0 || d[x].first != inf) {
    
    
                    continue;
                } else {
    
    
                    d[x].first = w + 1;
                    dis[x] = d[x].first;
                    q.push({
    
    x, d[x].first});
                    s.insert({
    
    d[x].first, {
    
    x, 0}});
                }
            }
        }
        while (!s.empty()) {
    
    
            auto [u, f] = s.begin()->second;
            s.erase(s.begin());
            for (auto v : rg[u]) {
    
    
                if (f == 0) {
    
    
                    if (dis[v] < dis[u]) {
    
    
                        if (d[v].first > d[u].first) {
    
    
                            auto it = s.find({
    
    d[v].first, {
    
    v, 0}});
                            if (it != s.end()){
    
    
                                s.erase(it);
                            }
                            d[v].first = d[u].first;
                            s.insert({
    
    d[v].first, {
    
    v, 0}});
                        }
                    }else {
    
    
                        if (d[v].second > d[u].first) {
    
    
                            auto it = s.find({
    
    d[v].second, {
    
    v, 1}});
                            if (it != s.end()){
    
    
                                s.erase(it);
                            }
                            d[v].second = d[u].first;
                            s.insert({
    
    d[v].second, {
    
    v, 1}});
                        }
                    }
                } else {
    
    
                    if (dis[v] < dis[u]) {
    
    
                        if (d[v].second > d[u].second) {
    
    
                            auto it = s.find({
    
    d[v].second, {
    
    v, 1}});
                            if (it != s.end()){
    
    
                                s.erase(it);
                            }
                            d[v].second = d[u].second;
                            s.insert({
    
    d[v].second, {
    
    v, 1}});
                        }
                    }
                }
            }
        }
        for (auto x : d) {
    
    
            cout << min(x.first, x.second) << " ";
        }
        cout << endl;
    }
    return 0;
}

Guess you like

Origin blog.csdn.net/zhouzi2018/article/details/112792753