最优化——贪心策略
Posted 牧空
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了最优化——贪心策略相关的知识,希望对你有一定的参考价值。
核心思想
- 总是选择当前情况下最优的策略,能够得到局部最优解。
- 但对于具备无后效性(即某个状态以前的过程不会影响以后的状态,只与当前状态有关)的问题,贪心策略可以获得全局最优解
例子
简单贪心
一个笼子里面关了鸡和兔子(鸡有2只脚,兔子有4只脚,没有例外)。已经知道了笼子里面脚的总数a,问笼子里面至少有多少只动物,至多有多少只动物
OJ
考虑最少,那么优先考虑兔子;考虑最多,优先考虑鸡
if(a % 2 == 0){
max = a / 2;
min = a / 4 + (a % 4) / 2;
}
区间贪心
OJ
两地之间有多个加油站,但每个加油站油价不同,如何以最少的价格到达目的地,或者最远到达哪个位置
- 加最便宜的油,跑最远的路
- 只要有更便宜的,就不多跑,刚好到加油站
参考柳神代码
struct Station
{
double price;
int distance;
bool operator<(const Station &b) const
{
if (distance == b.distance)
{
return price < b.price;
}
return distance < b.distance;
}
};
int main(int argc, char const *argv[])
{
int cmax, d, davg, n;
double sum;
while (scanf("%d %d %d %d", &cmax, &d, &davg, &n) != EOF)
{
vector<Station> stations(n + 1);
stations[n] = {0.0, d};
for (int i = 0; i < n; i++)
scanf("%lf %d", &stations[i].price, &stations[i].distance);
sort(stations.begin(), stations.end());
double nowDis = 0, maxDis = 0, nowPrice = 0, totalPrice = 0, leftDis = 0;
if (stations[0].distance != 0)
{
printf("The maximum travel distance = 0.00\\n");
return 0;
}
else
{
nowPrice = stations[0].price;
}
while (nowDis < d)
{
maxDis = nowDis + cmax * davg;
double minPriceDis = 0, minPrice = INT32_MAX;
int flag = 0;
for (int i = 1; i <= n && stations[i].distance <= maxDis; i++)
{
if (stations[i].distance <= nowDis)
continue;
// 只要有小于当前价格的加油站,就只跑到该加油站,不多跑,之后的路程使用该加油站的价格
if (stations[i].price < nowPrice)
{
totalPrice += (stations[i].distance - nowDis - leftDis) * nowPrice / davg;
leftDis = 0.0;
nowPrice = stations[i].price;
nowDis = stations[i].distance;
flag = 1;
break;
}
if (stations[i].price < minPrice)
{
minPrice = stations[i].price;
minPriceDis = stations[i].distance;
}
}
if (flag == 0 && minPrice != INT32_MAX)
{
totalPrice += (nowPrice * (cmax - leftDis / davg));
leftDis = cmax * davg - (minPriceDis - nowDis);
nowPrice = minPrice;
nowDis = minPriceDis;
}
if (flag == 0 && minPrice == INT32_MAX)
{
nowDis += cmax * davg;
printf("The maximum travel distance = %.2f\\n", nowDis);
return 0;
}
}
printf("%.2f\\n", totalPrice);
}
return 0;
}
以上是关于最优化——贪心策略的主要内容,如果未能解决你的问题,请参考以下文章
leetcode605. 种花问题贪心策略,局部区间最优解法
leetcode 763. 划分字母区间贪心策略:局部最优大区间划分