最短时间到达指定路口

【来源】网传的2018阿里秋招笔试题

【问题描述】

城市有 N 个路口,每个路口有自己编号,从0 ~ N-1, 每个路口有自己的交通控制信号,比如 0,3 表示 0 号路口的交通信号每隔 3 个时刻变化一次,即0,1,2时刻可以过,而3,4,5时刻不能过,而6,7,8时刻又可以过,以次类推,所有路口的允许时刻都从 0 时刻开始。城市有 M 条道路把这 N 个路口连接起来,0,1,4 表示该道路联通路口 0 和路口 1,道路通过距离需要 4 个时刻。现指定出发路口和终点路口,由 0 时刻出发,最快能在什么时间到达?

【输入】

N路口的个数 N个路口,第一列是路口id,第二列是该路口通行周期 M 路的条数 M条路,第一列路一端的路口,第二列路另一端的路口,第三列通行所需要的时间 S起点,T目标点
【输出】
最短时间
【输入范例】
9
0,3
1,5
2,7
3,3
4,5
5,7
6,9
7,3
8,5
14
0,1,4
0,7,8
1,2,8
1,7,11
2,3,7
2,5,4
2,8,2
3,4,9
3,5,14
4,5,10
5,6,2
6,8,6
6,7,1
7,8,7
0,4
【输出范例】
28

【算法思路】

这个题目与滴滴笔试题:青蛙走迷宫,最快走到出口是完全同一类型的题目,下面用递归分治法解。

当然可能有好的其他算法,下次再尝试。

【程序】

 1 #include <iostream>
 2 #include <vector>
 3 #include <numeric>
 4 #include <limits>
 5 
 6 using namespace std;
 7 
 8 int minTime=1e10;
 9 int steps;
10 
11 void travel(int intersections[][2], int roads[][3], int M, int N, int s, int t, int nowTime)
12 {
13 
14     if( s==t ){  //抵达终点后
15         if (minTime > nowTime){  //剩余最大体力值存入全局变量Max
16             minTime = nowTime;
17         }
18         return;
19     }
20     if(steps == 0)
21         return;
22 
23     int ori = nowTime;
24     for(int i = 0; i < M; i++){
25         if(roads[i][0] == s){
26             nowTime += roads[i][2];
27             int tmp;
28             for(int j = 0; j < N; j++){
29                 if(intersections[j][0] == roads[i][1]){
30                     if( roads[i][1] != t ){  //未抵达终点,加上该路口等待时间
31                         tmp = nowTime% (2*intersections[j][1]);
32                         if( tmp >= intersections[j][1] ){
33                             nowTime += 2*intersections[j][1] - tmp;
34                         }
35                     }
36                     break;
37                 }
38             }
39             steps--;
40             travel(intersections, roads, M, N, roads[i][1], t, nowTime);
41             steps++;
42             nowTime = ori;
43 
44         }else if(roads[i][1] == s){
45             nowTime += roads[i][2];
46             int tmp;
47             for(int j = 0; j < N; j++){
48                 if(intersections[j][0] == roads[i][0]){
49                     if( roads[i][0] != t ){  //未抵达终点,加上该路口等待时间
50                         tmp = nowTime% (2*intersections[j][1]);
51                         if( tmp >= intersections[j][1] ){
52                             nowTime += 2*intersections[j][1] - tmp;
53                         }
54                     }
55                     break;
56                 }
57             }
58             steps--;
59             travel(intersections, roads, M, N, roads[i][0], t, nowTime);
60             steps++;
61             nowTime = ori;
62         }
63     }
64 }
65 
66 
67 int main() {
68     int res;
69 
70     int _N=9;
71     int _M=14;
72     int _s=0;
73     int _t=4;
74 
75     int _intersections[][2]={{0,3},{1,5},{2,7},{3,3},{4,5},{5,7},{6,9},{7,3},{8,5}};
76     int _roads[][3]={{0,1,4},{0,7,8},{1,2,8},{1,7,11},{2,3,7},{2,5,4},{2,8,2},{3,4,9},{3,5,14},{4,5,10},{5,6,2},{6,8,6},{6,7,1},{7,8,7}};
77 
78     steps = _M;
79     travel(_intersections, _roads, _M, _N, _s, _t, 0);
80     cout << minTime << endl;
81 
82     return 0;
83 }

 

posted @ 2017-08-29 10:16  hedgehog小子  阅读(324)  评论(0编辑  收藏  举报