• poj-3268最短路



    title: poj-3268最短路
    date: 2018-10-13 15:54:34
    tags:

    • acm
    • 刷题
      categories:
    • ACM-最短路

    概述

    这是一道最短路的模板题,,,不过虽然是模板题,,,还是有一些细节的,,,,QAQ

    刚开始我的思路是建立一个汇点,,,然后求这个点为起点到终点x的最短路,,,再求终点到汇点的最短路,,,最后找一个和最大的,,,,这么想是因为和之前做的一道题很像,,,但像归像,,,终究不一样的,,,,这样还是求不出最后的结果,,,因为即使求出汇点到终点的最短路,,,但并不是每个点到终点的最短路,,,QAQ

    分析思路

    首先确定是单元最短路有关的题,,,而且题目保证正边,,,所以选择dijkstra解决,,,

    其次,,,我之前好像还是单源最短路的理解不够清楚,,,

    单源最短路一个最主要的性质就是所选起点到任意一点的最短路都可以求出来

    这道题分成两部分,,一部分是所有点到终点x的最短路,,,另一个是终点到所有点的最短路,,,

    显然后一部分可以直接调用一次dijkstra便可以求出,,,

    而前者可以考虑反方向,,,所有点到终点的最短路就相当于沿相同的最短路从 终点x 到 每个点 的最短路,,,这个相同的最短路就是指:假如1到3的最短路是1->4->3那么他就等同于3->4->1,,,所以再求前一部分就可以将图中的每一条路的方向都取反方向,,,也就是逆图,,,这样一终点x为起点到各点的最短路就等于各点到终点x的最短路,,,

    所以为了实现逆图选择 邻接矩阵 要比其他方式的存图要好一些,,,

    实现

    #include <iostream>
    #include <cstdio>
    #include <cstdlib>
    #include <queue>
    #include <algorithm>
    #include <cstring>
    
    using namespace std;
    
    const int maxn = 1e3 + 10;
    //const int maxm = 1e5 + 10;
    const int inf = 0x3f3f3f3f;
    
    int cost[maxn][maxn];
    bool vis[maxn];
    int dis1[maxn];
    int dis2[maxn];
    int cnt;
    int n , m , x;
    
    void dijkstra(int n , int s , int dis[] , int cost[][maxn])
    {
        //init
        for(int i = 1; i <= n; ++i)
            dis[i] = (i == s) ? 0 : inf;
        memset(vis , false , sizeof(vis));
    
        for(int i = 0; i < n; ++i)
        {
            int k = -1;
            int m = inf;
            for(int j = 1; j <= n; ++j)
            {
                if(!vis[j] && dis[j] < m)
                {
                    m = dis[j];
                    k = j;
                }
            }
            if(k == -1) break;
            vis[k] = true;
            for(int j = 1; j <= n; ++j)
                if(!vis[j] && dis[k] + cost[k][j] < dis[j])
                    dis[j] = dis[k] + cost[k][j];
        }
    }
    
    int main()
    {
        int u , v , w;
        while(scanf("%d%d%d" , &n , &m , &x) != EOF)
        {
            for(int i = 1; i <= n; ++i)
                for(int j = 1; j <= n; ++j)
                {
                    if(i == j)  cost[i][j] = 0;
                    else        cost[i][j] = inf;
                }
            for(int i = 1; i <= m; ++i)
            {
                scanf("%d%d%d" , &u , &v , &w);
                cost[u][v] = min(cost[u][v] , w);
            }
            dijkstra(n , x , dis1 , cost);
            for(int i = 1; i <= n; ++i)
                for(int j = 1; j < i; ++j)
                    swap(cost[i][j] , cost[j][i]);
            dijkstra(n , x , dis2 , cost);
    
            int ans = 0;
            for(int i = 1; i <= n; ++i)
                ans = max(ans , dis1[i] + dis2[i]);
    
            printf("%d
    " , ans);
        }
    }
    

    (end)

    什么时候才能真正的感觉这才是水题啊,,,QAQ

    剑之所指,心之所向,身之所往!!!
  • 相关阅读:
    HDFS snapshot操作实战
    不是技术牛人,如何拿到国内IT巨头的Offer(转载)
    HBase的RowKey设计原则
    hbase shell 基本命令总结
    13_Python数据类型字符串加强_Python编程之路
    监督学习与无监督学习的区别_机器学习
    12_Python的(匿名函数)Lambda表达式_Python编程之路
    Python数据挖掘_Python2模块Spynner的安装(安装失败)
    06_Linux目录文件操作命令3查找命令_我的Linux之路
    python数据挖掘_Json结构分析
  • 原文地址:https://www.cnblogs.com/31415926535x/p/9783279.html
Copyright © 2020-2023  润新知