@[TOC](LeetCode 983. Minimum Cost For Tickets车票的最小花费(DP))
题目描述
解题思路
这与典型的背包问题十分相似,可以把题目中旅行的天数days看作是背包的总容量,把票看作是装入背包的物品,票价代表物品价值,票的有效期代表物品重量。
记F[i]为总票价,i为日期,F[0]=0。为了便于使用动态规划算法,可以将不出行的日子也填满,则不出行那天的F[i]=F[i-1]。出行那天的票价有三种选择:
①F[i]=F[i-1]+costs[0]
(即出行当天买一张单日票,票价为一天前的总价加上单日票价)
②F[i]=F[i-7]+costs[1]
(即七天前就购买七日票,票价为七天前的总价加上七日票价)
③F[I]=F[i-30]+costs[2]
(即三十天前就购买月票,票价为三十天前的总价加上月票价)
因为days是是一个顺序排列的日期,日期按从小到大排列,故在从F[1]开始构造时,只用一个下标j追踪还未被考虑到的日期,每当days中的一个日期被访问过后j++。
代码
class Solution {
public:
int mincostTickets(vector<int>& days, vector<int>& costs) {
int lastdata=days[days.size()-1];
vector<int>F(lastdata+1,INT_MAX);
F[0]=0;
int j=0;
for(int i=1;i<=lastdata;i++)
{
if(i!=days[j])F[i]=F[i-1];
else
{
int mincost=F[i-1]+costs[0];
mincost=min(mincost,F[max(0,i-7)]+costs[1]);
mincost=min(mincost,F[max(0,i-30)]+costs[2]);
F[i]=mincost;
j++;
}
}
return F[lastdata];
}
};