嗯。。还是算法复习用到了的,竟然还有OJ上有这道题,所以过了一下
大体思路就是首先分点,记录同一位置不同剩余油量的花费。
int cost[N+1][N+1][K+1];
然后从起点开始一点一点扩展,分别判断有和没有加油站的情况走到4个方向上是否是更优的花费。有点儿类似Dijkstra最短路的感觉。
上代码

1 #include <iostream>
2 #include <queue>
3 #include <cstring>
4 #include <cstdio>
5 #include <cmath>
6 using namespace std;
7 #define ll long long
8 //template<typename T>
9 //inline T min(const T& a, const T& b) { return a < b? a:b;}
10 //template<typename T>
11 //inline T max(const T& a, const T& b) { return a > b? a:b;}
12
13 const int N = 100;
14 const int K = 10;
15 const int dirs[][2] = {{ -1, 0}, {1, 0}, {0, -1}, {0, 1}};
16
17 struct Position
18 {
19 int x, y, k;
20 };
21
22 queue<Position> que;
23 int cm[N + 1][N + 1][K + 1];
24 int map[N + 1][N + 1];
25 int inqueue[N + 1][N + 1][K + 1];
26 int n, k, a, b, c;
27
28 bool isValid(int x, int y)
29 {
30 if(x < 1
31 || x > n
32 || y < 1
33 || y > n)
34 {
35 return false;
36 }
37 return true;
38 }
39
40 void init()
41 {
42 memset(cm, -1, sizeof(cm));
43 cm[1][1][k] = 0;
44 memset(map, 0, sizeof(map));
45 memset(inqueue, 0, sizeof(inqueue));
46 while(!que.empty())
47 {
48 que.pop();
49 }
50 }
51
52 void checkBetter(int x, int y, int k, int cost)
53 {
54 // If is better to go to (x, y) from (p.x, p.y)
55 if(cm[x][y][k] == -1 || cm[x][y][k] > cost)
56 {
57 cm[x][y][k] = cost;
58 if(inqueue[x][y][k] == 0)
59 {
60 Position tem;
61 tem.x = x;
62 tem.y = y;
63 tem.k = k;
64 que.push(tem);
65 inqueue[tem.x][tem.y][tem.k] = 1;
66 }
67 }
68 }
69
70 int driveCar()
71 {
72 Position pos;
73 pos.x = pos.y = 1;
74 pos.k = k;
75 inqueue[1][1][k] = 1;
76 que.push(pos);
77
78 while(!que.empty())
79 {
80 Position p = que.front();
81 que.pop();
82 inqueue[p.x][p.y][p.k] = 0;
83 for(int d = 0; d != 4; d++)
84 {
85 int dx = dirs[d][0], dy = dirs[d][1];
86 int x = p.x + dx, y = p.y + dy;
87
88 if(isValid(x, y))
89 {
90 int cost = cm[p.x][p.y][p.k];
91 if(dx < 0)
92 {
93 cost += b;
94 }
95 if(dy < 0)
96 {
97 cost += b;
98 }
99
100 // No station.
101 if(p.k > 0 && map[p.x][p.y] == 0)
102 {
103 // If is better to go to (x, y) from (p.x, p.y)
104 checkBetter(x, y, p.k - 1, cost);
105 }
106 // Has station, ether a new built one, or one already exists.
107 cost += a;
108 if(map[p.x][p.y] == 0)
109 {
110 cost += c;
111 }
112 // Add fuel and check again
113 checkBetter(x, y, k - 1, cost);
114 }
115 }
116 }
117
118 int mincost = 0x7fffffff;
119 for(int i = 0; i <= k; i++)
120 {
121 if(cm[n][n][i] > 0 && mincost > cm[n][n][i])
122 {
123 mincost = cm[n][n][i];
124 }
125 }
126 return mincost;
127 }
128
129 int main()
130 {
131 #ifdef ACM_LOCAL
132 freopen("input.txt", "r", stdin);
133 //freopen("output.txt", "w", stdout);
134 #endif // ACM_LOCAL
135
136 while(scanf("%d%d%d%d%d", &n, &k, &a, &b, &c) != EOF)
137 {
138 init();
139
140 for(int i = 1; i <= n; i++)
141 for(int j = 1; j <= n; j++)
142 {
143 scanf("%d", &map[i][j]);
144 }
145
146 printf("%d\n", driveCar());
147 }
148
149 #ifdef ACM_LOCAL
150 printf("Used time: %lf\n", clock() / (double) CLOCKS_PER_SEC);
151 #endif // ACM_LOCAL
152 return 0;
153 }
速度还是挺快的:
|
Accepted
|
36MS
|
1128K
|
3449Byte
|
2013-12-23 15:11:43.0
|
不过Candesoft-BLOG里说的分层图最短路的没有仔细看。
来源:https://www.cnblogs.com/tech-cabin/p/Car_Drive_With_Fuel.html
