zoukankan      html  css  js  c++  java
  • 洛谷P1119|灾后重建|最短路|Floyd|Floyd的拓展

    题目描述

    分析

    考虑本题:
    只通过修好的前几个村庄,从i->j的最短路,联想到
    Flyod算法:
    初始化:

    f[][]=INF;
    f[i][i]=0; 
    for(int k=1;k<=n;k++)
    	for(int i=1;i<=n;i++)
    		for(int j=1;j<=n;j++)
    			dist[i][j]=min(dist[i][j],dist[i][k]+dist[k][j]);
    
    

    考虑FLyod算法意义:
    k为中转点,i为起点,j为终点
    起点i->j如果只经过前k个点的最短距离
    考虑本题:
    因为只能经过修好的前几个村庄,则刚好对应了Floyd算法的k的意义。
    因为询问的t是递增的,所以不用进行排序。
    数据结构:
    利用了类似栈的思想(程序里面的head实质上是tail):
    因为t(包括每个村庄和询问)全是递增的,所以直接用栈首表示当前的时间的下标,如果当前下标的时间小于询问时间,则将中间断点增加一个

    代码

    #include <cstdio>
    #include <iostream>
    using namespace std;
    const int maxn=205;
    const int INF=9999999;
    int n,m;
    int dist[maxn][maxn],ct[maxn]/*完成的时间*/;
    int head=0/*表示前head个村庄重建*/;
    void init(){
    	scanf("%d%d",&n,&m);
    	for(int i=0;i<n;i++) scanf("%d",&ct[i]);
    	for(int i=0;i<n;i++)
    		for(int j=0;j<n;j++) dist[i][j]=INF;
    	for(int i=0;i<n;i++) dist[i][i]=0;
    	for(int i=1;i<=m;i++){
    		int u,v,w;scanf("%d%d%d",&u,&v,&w);
    		dist[u][v]=dist[v][u]=w;
    	}
    }
    void Floyd(int k){
    	for(int i=0;i<n;i++)
    		for(int j=0;j<n;j++)
    			dist[i][j]=dist[j][i]=min(dist[i][j],dist[i][k]+dist[k][j]);
    }
    void solve(){
    	int q;scanf("%d",&q);
    	while(q--){
    		int u,v,t;scanf("%d%d%d",&u,&v,&t);
    		while(ct[head]<=t&&head<n){//当前的时间足以让下一个修路 
    			Floyd(head);
    			head++;
    		}
    		if(ct[u]>t||ct[v]>t) printf("%d
    ",-1);
    		else printf("%d
    ",dist[u][v]==INF?-1:dist[u][v]);
    	}
    }
    int main(){
    	init();
    	solve();
    	return 0;
    }
    
    
  • 相关阅读:
    用DECODE进行排序
    linux下批量替换文件内容
    Linux下chkconfig命令详解
    linux 命令参数列表过长以及find用法
    参数上使用自定义注解在aop中无法获取到该参数
    AOP
    AOP aspect XML 配置
    AOP前世与今生,aspect
    ETL工具之——kettle使用简介
    ETL工具之kittle使用案例整理
  • 原文地址:https://www.cnblogs.com/saitoasuka/p/9931574.html
Copyright © 2011-2022 走看看