先手动模拟一下算法的流程,可以将走法总结如下(贪心算法):
- 如果到达范围内有比当前站更便宜的站,则加油加到刚好能到那个站。
- 如果到达范围内没有比当前站更便宜的站,那么将油加满,并且选择到达范围内最便宜(但是比当前站贵)的站。
#include<cstdio>
#include<algorithm>
using namespace std;
struct node {
double price;
double dis;
}station[500];
bool cmp(node n1, node n2) {
return n1.dis < n2.dis;
}
const int inf = 0x7fffffff;
int main() {
int capacity, distance, unitDis, stationNum;
scanf("%d%d%d%d", &capacity, &distance, &unitDis, &stationNum);
for (int i = 0;i < stationNum;i++) {
scanf("%lf%lf", &station[i].price, &station[i].dis);
}
station[stationNum].dis = inf;
sort(station, station + stationNum, cmp);
if (station[0].dis != 0) {
printf("The maximum travel distance = 0.00");
return 0;
}
int pos = 0; //目前位置
int maxTravel = capacity * unitDis; //最多可以走的距离
double cost = 0; //总花费
double remain = 0; //剩下的油量
while (station[pos].dis < distance) {
//找到到达范围内下一个更便宜的
int index = pos + 1,
nextCheaper = -1, //下一个比当前站便宜的站
minPricePos = -1; //到达范围内最便宜的站
while (station[index].dis <= station[pos].dis + maxTravel) {
if (station[index].price < station[pos].price) {
nextCheaper = index;
break;
}
if (minPricePos == -1 || station[index].price < station[minPricePos].price) {
minPricePos = index;
}
index++;
}
if (station[pos].dis + maxTravel >= distance && nextCheaper == -1) { //当前站可以直接到目的地,且中间没有更便宜的站
cost += (distance - station[pos].dis - remain * unitDis) / unitDis * station[pos].price;
break;
}
else if (nextCheaper == -1 && minPricePos == -1) { //到不了下一个站
printf("The maximum travel distance = %.2lf", station[pos].dis + maxTravel);
return 0;
}
else if (nextCheaper == -1) { //到达范围内没有更便宜的,加满,去到达范围内最便宜的
cost += (capacity - remain) * station[pos].price;
remain = capacity - (station[minPricePos].dis - station[pos].dis) / unitDis;
pos = minPricePos;
}
else {
cost += (station[nextCheaper].dis - station[pos].dis - remain * unitDis) / unitDis * station[pos].price;
remain = 0;
pos = nextCheaper;
}
}
printf("%.2lf", cost);
}