zoukankan      html  css  js  c++  java
  • Uva11374 Dijkstra

    机场快线是市民从市内去机场的首选交通工具。机场快线分为经济线和商业线两种,线路、速度和价格都不同,你有一张商业线车票,可以坐一站商业线,而其他时候,只能乘坐经济线。假设换乘时间忽略不计,你的任务是找一条去机场最快的路线。

    这样我们先从起点开始做一次dijkstra 然后在从终点开始做一次dijkstra, 然后枚举每个商业边。

    #include <iostream>
    #include <algorithm>
    #include <string.h>
    #include <cstdio>
    #include <vector>
    #include <queue>
    #include <algorithm>
    using namespace std;
    const int INF =1000000000;
    const int maxn = 500+10;
    struct Edge{
      int from,to,dist;
    };
    struct HeapNoda{
       int d,u;
       bool operator <(const HeapNoda &rhs)const{
         return d>rhs.d;
       }
    };
    struct Dijkstra{
          int n,m;
          vector<Edge> edges;
          vector<int>G[maxn];
          bool done[maxn];
          int d[maxn];
          int p[maxn];
          void inti(int n){
            this->n=n;
            for(int i=0; i<n; ++i) G[i].clear();
            edges.clear();
          }
          void AddEdge(int from, int to, int dist){
              edges.push_back((Edge){from,to,dist});
              m = edges.size();
              G[from].push_back(m-1);
          }
          void dijkstra(int s){
              priority_queue<HeapNoda> Q;
              for(int i=0; i<n; i++ ) d[i]=INF;
              d[s]=0;
              memset(done,0,sizeof(done));
              Q.push((HeapNoda){0,s});
              while(!Q.empty()){
                  HeapNoda x = Q.top(); Q.pop();
                  int u = x.u;
                  if(done[u]) continue;
                  done[u] =true;
                  for(int i=0; i<G[u].size(); ++i){
                     Edge &e = edges[G[u][i]];
                     if(d[e.to]>d[u]+e.dist){
                          d[e.to] = d[u] +e.dist;
                          p[e.to] = G[u][i];
                          Q.push((HeapNoda){d[e.to],e.to});
                     }
                  }
              }
          }
          void GetshortPaths(int s, int *dist, vector<int> *paths){
              dijkstra(s);
              for(int i=0; i<n; i++){
                  dist[i]=d[i];
                  paths[i].clear();
                  int t = i;
                  paths[i].push_back(t);
                  while(t!=s){
                      paths[i].push_back( edges[p[t]].from );
                      t = edges[ p[t] ].from;
                  }
                  reverse(paths[i].begin(),paths[i].end());
              }
          }
    };
    Dijkstra solver;
    int d1[maxn], d2[maxn];
    vector<int> paths1[maxn], paths2[maxn];
    int main()
    {
         int N,S,E,M,kase=0,X,Y,Z,K;
         while(scanf("%d%d%d",&N,&S,&E) == 3){
                S-- ; E--;
              scanf("%d",&M);
              solver.inti(N);
              for(int i=0; i<M; ++i){
                   scanf("%d%d%d",&X,&Y,&Z);X--; Y--;
                   solver.AddEdge(X,Y,Z);
                   solver.AddEdge(Y,X,Z);
              }
              solver.GetshortPaths(S,d1,paths1);
              solver.GetshortPaths(E,d2,paths2);
              int ans = d1[E];
              vector<int>path = paths1[E];
              int midpoint=-1;
              scanf("%d",&K);
              for(int i=0; i<K; ++i){
                   scanf("%d%d%d",&X,&Y,&Z); X--; Y--;
                   for(int j=0; j<2; j++){
                     if(d1[X]+d2[Y]+Z<ans){
                        ans=d1[X]+d2[Y]+Z;
                        path=paths1[X];
                        midpoint=X;
                        for(int a = paths2[Y].size()-1; a>=0; a--){
                            path.push_back( paths2[Y][a] );
                        }
                     }
                     swap(X,Y);
                   }
              }
              if(kase) printf("
    ");
              kase=1;
              for(int i=0; i<path.size()-1; i++)
                 printf("%d ",path[i]+1);
              printf("%d
    ",E+1);
              if(midpoint==-1) printf("Ticket Not Used
    ");
              else printf("%d
    ",midpoint+1);
              printf("%d
    ",ans);
         }
        return 0;
    }
    View Code
  • 相关阅读:
    Jenkins构建常见问题
    Jenkins搭建.NET自动编译发布远程环境
    Jenkins搭建.NET自动编译发布本地环境
    Web API系列(四) 使用ActionFilterAttribute 记录 WebApi Action 请求和返回结果记录
    C# 异步编程(async&await)
    [root@localhost ~]# /etc/httpd/conf/httpd.conf bash: /etc/httpd/conf/httpd.conf: 权限不够
    解决apache启动失败:Job for httpd.service failed.
    Windows环境下PHP配置详解
    如何以管理员身份运行cmd
    win8如何设置以管理员身份运行
  • 原文地址:https://www.cnblogs.com/Opaser/p/4319315.html
Copyright © 2011-2022 走看看