zoukankan      html  css  js  c++  java
  • [CF1473E] Minimum Path

    [CF1473E] Minimum Path - 分层图最短路

    Description

    给定一个无向图,定义路径的权值为路径上所有边权的和减去边权的极差。求 1 到其它所有点的最短路。

    Solution

    很妙的转化:一条边权值变成 0,一条边权值加倍,求最短路

    转化后的条件加上最短的条件,就得到了转化前的条件

    于是分层图最短路即可

    #include <bits/stdc++.h>
    using namespace std;
    
    #define int long long 
    
    #define reset(x) memset(x, 0, sizeof x)
    #define reset3f(x) memset(x, 0x3f, sizeof x)
    namespace sp
    {
        const int N = 1e+6 + 5;
        vector<pair<int, int>> g[N];
        int n, v0 = 1, d[N], v[N];
        void make(int t1, int t2, int t3)
        {
            g[t1].push_back(make_pair(t2, t3));
        }
        void reset_graph()
        {
            for (int i = 0; i <= n; i++)
                g[i].clear();
        }
        void solve()
        {
            priority_queue<pair<int, int>> qu;
            reset3f(d);
            reset(v);
            d[v0] = 0;
            qu.push(make_pair(0, v0));
            while (qu.size())
            {
                int p = qu.top().second, r = qu.top().first;
                qu.pop();
                if (r + d[p])
                    continue;
                for (int i = 0; i < g[p].size(); i++)
                {
                    int q = g[p][i].first, w = g[p][i].second;
                    if (d[q] > d[p] + w)
                    {
                        d[q] = d[p] + w;
                        qu.push(make_pair(-d[q], q));
                    }
                }
            }
        }
    } // namespace sp
    
    int n, m, s, t1, t2, t3;
    
    signed main()
    {
        cin >> n >> m;
        s = 1;
        int ORIGIND = 0;
        int DOUBLED = n * 2;
        int IGNORED = n;
        int DOUIGND = n * 3;
    
        for (int i = 1; i <= n; i++)
        {
            sp::make(i, i + n, 0);
            sp::make(i + 2 * n, i + 3 * n, 0);
            sp::make(i, i + 3 * n, 0);
        }
    
        for (int i = 1; i <= m; i++)
        {
            cin >> t1 >> t2 >> t3;
    
            sp::make(t1 + ORIGIND, t2 + ORIGIND, t3);
            sp::make(t1 + DOUBLED, t2 + DOUBLED, t3);
            sp::make(t1 + IGNORED, t2 + IGNORED, t3);
            sp::make(t1 + DOUIGND, t2 + DOUIGND, t3);
    
            sp::make(t1 + ORIGIND, t2 + DOUBLED, t3 * 2);
            sp::make(t1 + IGNORED, t2 + DOUIGND, t3 * 2);
    
            sp::make(t1 + ORIGIND, t2 + IGNORED, 0);
            sp::make(t1 + DOUBLED, t2 + DOUIGND, 0);
    
            swap(t1, t2);
    
            sp::make(t1 + ORIGIND, t2 + ORIGIND, t3);
            sp::make(t1 + DOUBLED, t2 + DOUBLED, t3);
            sp::make(t1 + IGNORED, t2 + IGNORED, t3);
            sp::make(t1 + DOUIGND, t2 + DOUIGND, t3);
    
            sp::make(t1 + ORIGIND, t2 + DOUBLED, t3 * 2);
            sp::make(t1 + IGNORED, t2 + DOUIGND, t3 * 2);
    
            sp::make(t1 + ORIGIND, t2 + IGNORED, 0);
            sp::make(t1 + DOUBLED, t2 + DOUIGND, 0);
        }
    
        sp::solve();
    
        for (int i = 2; i <= n; i++)
        {
            cout << sp::d[i + DOUIGND] << " ";
        }
    }
    
    
  • 相关阅读:
    OnContextMenu事件
    wireshark教程
    常见的算法题:逆行单一列表
    GPIO
    USB OTG简要
    软测验点---平衡二叉树
    SSL工作原理
    CFileDialog 使用简单介绍
    eclipse在maven项目交付svn忽略简介
    四个漂亮CSS样式表
  • 原文地址:https://www.cnblogs.com/mollnn/p/14340725.html
Copyright © 2011-2022 走看看