完美秋招真题——最短最优升级路径

//通过全部测试
import java.util.ArrayList;
import java.util.HashSet;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Scanner;
import java.util.Set;

public class Main {

public   static   List<Integer>  removeDuplicateWithOrder(List<Integer> list)   { 
      Set <Integer>set  =   new  HashSet<Integer>(); 
      List <Integer>newList  =   new  ArrayList<Integer>(); 
   for  (Iterator iter  =  list.iterator(); iter.hasNext();)   { 
         int element  =  (Integer) iter.next(); 
         if  (set.add(element)) 
            newList.add(element); 
     } 
     list.clear(); 
     list.addAll(newList); 
    return list;
} 
public static void main(String[] args) {
     Scanner scan=new Scanner(System.in);
     int start=scan.nextInt();
     int end=scan.nextInt();
     int sum=0;
     List<Integer>listStart=new ArrayList<Integer>();
     List<Integer>listEnd=new ArrayList<Integer>();
     List<Integer>listSize=new ArrayList<Integer>();
     List<Integer>temp=new ArrayList<Integer>();


     while(scan.hasNext()){
         int s1=scan.nextInt();
         int e1=scan.nextInt();
         int size=scan.nextInt();
         listStart.add(s1);
         listEnd.add(e1);
         listSize.add(size);
         temp.add(s1);
         temp.add(e1);

     }
     scan.close();
     //相当于寻找图中的最小路径
     ArrayList<ArrayList<Integer>> path=new ArrayList<ArrayList<Integer>>();


     //path.add(start);
     //统计图中的节点数
     List<Integer> nodes=removeDuplicateWithOrder(temp);
     int[][]arr=new int[nodes.size()][nodes.size()];
     for(int i=0;i<nodes.size();i++){
         for(int j=0;j<nodes.size();j++){
             arr[i][j]=Integer.MAX_VALUE;
         }
     }
     for(int i=0;i<nodes.size();i++){
            List<Integer>xx=new ArrayList<Integer>();
            path.add((ArrayList<Integer>) xx);
        }
     //第一步初始化出发节点到各个节点的距离
     for(int i=0;i<listStart.size();i++){
         int x=nodes.indexOf(listStart.get(i));
         int y=nodes.indexOf(listEnd.get(i));
         arr[x][y]=listSize.get(i);
     }
     int D[]=new int[nodes.size()];
     boolean tag[]=new boolean[nodes.size()];
     for(int i=0;i<tag.length;i++){
         tag[i]=false;
     }
     tag[0]=true;
     for(int i=0;i<nodes.size();i++){
         D[i]=arr[0][i];

     }
     for(int k=0;k<nodes.size();k++){
         int min=Integer.MAX_VALUE,node=0;
         for(int i=0;i<nodes.size();i++){
             if(tag[i]==false){
                 if(D[i]<min){
                     min=D[i];
                     node=i;
                 }
             }
         }
         path.get(node).add(temp.get(node));
         tag[node]=true;
         if(temp.indexOf(end)==node){
             sum=min;
             break;
         }
         //更新新添加的节点进来后的距离
         for(int i=0;i<nodes.size();i++){
             //如果当前最小值节点到各个顶点有边
             if(arr[node][i]!=Integer.MAX_VALUE){
                 if(min+arr[node][i]<D[i]){
                     D[i]=min+arr[node][i];
                     //更改了当前值,则把路径加入到该节点
                     path.get(i).clear();
                     for(int n=0;n<path.get(node).size();n++){
                         path.get(i).add(path.get(node).get(n));
                     }
                 }
             }
         }
     }

     String s=""+start;
     for(int i=0;i<path.get(temp.indexOf(end)).size();i++){
         s=s+"->"+path.get(temp.indexOf(end)).get(i);
     }
     s=s+"("+sum+")";
     System.out.println(s);
}

}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值